Class SulfurDepositionAnalyser
- All Implemented Interfaces:
Serializable, Runnable, ProcessEquipmentInterface, TwoPortInterface, ProcessElementInterface, SimulationInterface, NamedInterface
This unit operation combines multiple analysis capabilities for understanding sulfur behaviour in gas value chains (offshore and onshore):
- Chemical equilibrium: Uses the Gibbs reactor to compute equilibrium products from H2S and O2 reactions, including S8, SO2, SO3, and sulfuric acid formation.
- Sulfur solubility: Calculates S8 solubility in the gas phase at given conditions and identifies precipitation (solid formation) via TP-solid flash.
- Temperature sweep: Scans across a range of temperatures to find the onset temperature for solid sulfur deposition and maps the deposition profile.
- Corrosion assessment: Evaluates FeS (iron sulfide) formation potential and corrosion risk from H2S and SO2 in the presence of water.
Key Reactions Modelled
| Reaction | Description |
|---|---|
| 2 H2S + O2 = 2 H2O + 1/4 S8 | Direct oxidation of H2S (Claus reaction) |
| 2 H2S + 3 O2 = 2 SO2 + 2 H2O | Full oxidation of H2S |
| 3 H2S + SO2 = 4 S + 2 H2O | Claus tail gas reaction |
| H2S + Fe = FeS + H2 | Iron sulfide (corrosion) formation |
Usage Example
SystemInterface gas = new SystemSrkEos(273.15 + 50, 70.0);
gas.addComponent("methane", 0.93);
gas.addComponent("H2S", 0.0001);
gas.addComponent("oxygen", 0.00001);
gas.addComponent("CO2", 0.02);
gas.addComponent("S8", 1e-8);
gas.addComponent("SO2", 0.0);
gas.addComponent("water", 0.001);
gas.setMixingRule(2);
Stream feed = new Stream("feed", gas);
feed.setFlowRate(100000, "kg/hr");
feed.run();
SulfurDepositionAnalyser analyser = new SulfurDepositionAnalyser("Sulfur Analyser", feed);
analyser.setTemperatureSweepRange(0, 200, 5); // 0-200 C in 5 C steps
analyser.run();
// Get results
String report = analyser.getResultsAsJson();
double onsetTemp = analyser.getSulfurDepositionOnsetTemperature();
double s8Solubility = analyser.getSulfurSolubilityInGas();
boolean corrosionRisk = analyser.hasCorrosionRisk();
- Version:
- 1.0
- Author:
- Even Solbraa
- See Also:
-
Field Summary
FieldsModifier and TypeFieldDescriptionprivate doubleprivate doubleprivate doubleprivate doubleprivate intprivate doubleprivate static final org.apache.logging.log4j.LoggerLogger.private static final doubleConversion factor from mol fraction to mg/Sm3.private doubleprivate doubleprivate booleanprivate booleanprivate booleanprivate static final doubleMolar mass of S8 in kg/mol.private static final longSerialization version UID.private doubleprivate booleanprivate doubleprivate doubleprivate doubleprivate doubleprivate doubleprivate doubleFields inherited from class TwoPortEquipment
inStream, outStreamFields inherited from class ProcessEquipmentBaseClass
conditionAnalysisMessage, energyStream, hasController, isSolved, properties, reportFields inherited from class SimulationBaseClass
calcIdentifier, calculateSteadyState, timeFields inherited from class NamedBaseClass
name -
Constructor Summary
ConstructorsConstructorDescriptionCreates a new SulfurDepositionAnalyser.SulfurDepositionAnalyser(String name, StreamInterface stream) Creates a new SulfurDepositionAnalyser with an inlet stream. -
Method Summary
Modifier and TypeMethodDescriptionprivate voidaddEquipmentRisk(List<Map<String, String>> list, String equipment, String riskLevel, String description) Adds an equipment risk entry to the equipment risk list.Gets the blockage risk assessment results.Gets the catalysis analysis results including all evaluated pathways, composition effects, and dominant mechanism assessment.private doublegetComponentMolFrac(SystemInterface sys, String name) Gets the mole fraction of a component from the system, returning 0 if not present.Gets the corrosion assessment results.Gets the equilibrium composition after Gibbs reactor calculation.Gets the gas vs liquid S8 solubility comparison results.Gets the kinetic analysis results including reaction rates, FeS corrosion rate, root cause classification, and wall loss estimates.Gets the reaction summary from the Gibbs equilibrium calculation.Returns comprehensive results as a JSON string.doubleGets the solid sulfur phase fraction at inlet conditions.doubleGets the temperature at which solid sulfur first deposits (in Celsius).doubleGets the sulfur solubility in the gas phase as mole fraction.doubleGets the sulfur solubility in the gas phase in mg/Sm3.Gets the supersaturation and nucleation analysis results.Gets the temperature sweep results.booleanReturns true if any corrosion risk is identified.booleanReturns true if solid sulfur is present at inlet conditions.private com.google.gson.JsonObjectmapToJsonObject(Map<String, Object> map) Converts a map to a JsonObject, handling nested Lists and Maps recursively.private voidperformBlockageRiskAssessment(StreamInterface inlet, double pressure) Assesses the risk of pipeline or equipment blockage from sulfur deposition.private voidperformCatalysisAnalysis(StreamInterface inlet, double pressure) Evaluates catalytic pathways for elemental sulfur formation from the gas composition.private voidperformChemicalEquilibrium(StreamInterface inlet, double pressure) Performs Gibbs free energy minimisation to determine equilibrium products from H2S and O2 reactions at the inlet conditions.private voidperformCorrosionAssessment(StreamInterface inlet, double pressure) Assesses corrosion risk from sulfur species and CO2.private voidperformGasVsLiquidSolubilityComparison(StreamInterface inlet, double pressure) Compares S8 solubility in gas phase versus liquid hydrocarbon phase.private voidperformKineticAnalysis(StreamInterface inlet, double pressure) Performs kinetic analysis of sulfur-related reactions.private voidperformSulfurSolubilityAnalysis(StreamInterface inlet, double pressure) Analyses sulfur solubility in the gas phase and checks for solid S8 formation using TP-solid flash at inlet conditions.private voidperformSupersaturationAnalysis(StreamInterface inlet, double pressure) Analyses the supersaturation state of dissolved S8 and estimates nucleation risk using classical nucleation theory.private voidperformTemperatureSweep(StreamInterface inlet, double pressure) Sweeps temperature to find the sulfur deposition onset temperature and build a deposition profile.voidPrints a human-readable summary of the analysis results to the logger.voidIn this method all thermodynamic and unit operations will be calculated in a steady state calculation.voidsetAnalysisPressure(double pressureBara) Sets the pressure for the analysis (default: use inlet pressure).voidsetFlowVelocity(double velocityMs) Sets gas flow velocity for blockage risk calculations.voidsetGasFlowRate(double flowRateSm3h) Sets gas flow rate at standard conditions for blockage risk calculations.voidsetGibbsDamping(double damping) Sets Gibbs reactor damping factor.voidsetGibbsMaxIterations(int maxIter) Sets Gibbs reactor max iterations.voidsetGibbsTolerance(double tolerance) Sets Gibbs reactor convergence tolerance.private voidsetHydrocarbonInert(GibbsReactor reactor, SystemInterface sys) Marks hydrocarbon components as inert in the Gibbs reactor so they do not participate in reactions.voidsetPipeDiameter(double diameterM) Sets pipe diameter for blockage risk calculations.voidsetPipeSegmentLength(double lengthM) Sets pipe segment length for blockage risk calculations.voidsetRunChemicalEquilibrium(boolean enabled) Enables or disables chemical equilibrium calculation.voidsetRunCorrosionAssessment(boolean enabled) Enables or disables corrosion assessment.voidsetRunSolidFlash(boolean enabled) Enables or disables solid flash calculation.voidsetTemperatureSweepRange(double startC, double endC, double stepC) Sets the temperature range for the deposition sweep analysis.Methods inherited from class TwoPortEquipment
getInletPressure, getInletStream, getInletStreams, getInletTemperature, getMassBalance, getOutletPressure, getOutletStream, getOutletStreams, getOutletTemperature, setInletPressure, setInletStream, setInletTemperature, setOutletPressure, setOutletPressure, setOutletStream, setOutletTemperature, setOutletTemperature, toJson, toJson, validateSetupMethods inherited from class ProcessEquipmentBaseClass
addCapacityConstraint, addController, copy, displayResult, equals, getAvailableMargin, getAvailableMarginPercent, getBottleneckConstraint, getCapacityConstraints, getConditionAnalysisMessage, getConstraintEvaluationReport, getController, getController, getControllers, getEffectiveCapacityFactor, getEnergyStream, getEntropyProduction, getExergyChange, getFailureMode, getMassBalance, getMaxUtilization, getMaxUtilizationPercent, getMechanicalDesign, getMinimumFlow, getPressure, getPressure, getProperty, getReferenceDesignation, getReport_json, getResultTable, getSpecification, getTemperature, getTemperature, getThermoSystem, getUtilizationSummary, hashCode, initElectricalDesign, initializeDefaultConstraints, initInstrumentDesign, initMechanicalDesign, isActive, isActive, isCapacityAnalysisEnabled, isCapacityExceeded, isFailed, isHardLimitExceeded, isNearCapacityLimit, isSetEnergyStream, reportResults, restoreFromFailure, run_step, runConditionAnalysis, setCapacityAnalysisEnabled, setController, setEnergyStream, setEnergyStream, setFailureMode, setFlowValveController, setMinimumFlow, setPressure, setReferenceDesignation, setRegulatorOutSignal, setSpecification, setTemperature, simulateDegradedOperation, simulateTrip, solvedMethods inherited from class SimulationBaseClass
getCalculateSteadyState, getCalculationIdentifier, getTime, increaseTime, isRunInSteps, setCalculateSteadyState, setCalculationIdentifier, setRunInSteps, setTimeMethods inherited from class NamedBaseClass
getName, getTagNumber, setName, setTagNumberMethods inherited from class Object
clone, finalize, getClass, notify, notifyAll, toString, wait, wait, waitMethods inherited from interface NamedInterface
getName, getTagName, getTagNumber, setName, setTagName, setTagNumberMethods inherited from interface ProcessEquipmentInterface
getCapacityDuty, getCapacityMax, getElectricalDesign, getEquipmentState, getExergyChange, getExergyDestruction, getExergyDestruction, getFluid, getInstrumentDesign, getOperatingEnvelopeViolation, getOutletFlowRate, getOutletPressure, getOutletTemperature, getReferenceDesignationString, getRestCapacity, getSimulationValidationErrors, isSimulationValid, isWithinOperatingEnvelope, needRecalculationMethods inherited from interface SimulationInterface
getCalculateSteadyState, getCalculationIdentifier, getTime, increaseTime, isRunInSteps, run, run_step, runTransient, runTransient, setCalculateSteadyState, setCalculationIdentifier, setRunInSteps, setTimeMethods inherited from interface TwoPortInterface
getInStream, getOutStream, setOutPressure, setOutPressure, setOutTemperature, setOutTemperature
-
Field Details
-
serialVersionUID
private static final long serialVersionUIDSerialization version UID.- See Also:
-
logger
private static final org.apache.logging.log4j.Logger loggerLogger. -
S8_MOLAR_MASS
private static final double S8_MOLAR_MASSMolar mass of S8 in kg/mol.- See Also:
-
MOL_FRAC_TO_MG_SM3
private static final double MOL_FRAC_TO_MG_SM3Conversion factor from mol fraction to mg/Sm3.- See Also:
-
tempSweepStartC
private double tempSweepStartC -
tempSweepEndC
private double tempSweepEndC -
tempSweepStepC
private double tempSweepStepC -
analysisPressueBara
private double analysisPressueBara -
runChemicalEquilibrium
private boolean runChemicalEquilibrium -
runSolidFlash
private boolean runSolidFlash -
runCorrosionAssessment
private boolean runCorrosionAssessment -
gibbsMaxIterations
private int gibbsMaxIterations -
gibbsDamping
private double gibbsDamping -
gibbsTolerance
private double gibbsTolerance -
sulfurSolubilityMolFrac
private double sulfurSolubilityMolFrac -
sulfurSolubilityMgSm3
private double sulfurSolubilityMgSm3 -
sulfurDepositionOnsetTemperatureC
private double sulfurDepositionOnsetTemperatureC -
solidSulfurPresent
private boolean solidSulfurPresent -
solidSulfurFraction
private double solidSulfurFraction -
equilibriumComposition
-
temperatureSweepResults
-
corrosionAssessment
-
reactionSummary
-
kineticAnalysis
-
supersaturationAnalysis
-
gasVsLiquidSolubility
-
blockageRiskAssessment
-
catalysisAnalysis
-
pipeDiameterM
private double pipeDiameterM -
pipeSegmentLengthM
private double pipeSegmentLengthM -
flowVelocityMs
private double flowVelocityMs -
gasFlowRateSm3h
private double gasFlowRateSm3h
-
-
Constructor Details
-
SulfurDepositionAnalyser
Creates a new SulfurDepositionAnalyser.- Parameters:
name- equipment name
-
SulfurDepositionAnalyser
Creates a new SulfurDepositionAnalyser with an inlet stream.- Parameters:
name- equipment namestream- inlet stream
-
-
Method Details
-
setTemperatureSweepRange
public void setTemperatureSweepRange(double startC, double endC, double stepC) Sets the temperature range for the deposition sweep analysis.- Parameters:
startC- start temperature in CelsiusendC- end temperature in CelsiusstepC- step size in Celsius
-
setAnalysisPressure
public void setAnalysisPressure(double pressureBara) Sets the pressure for the analysis (default: use inlet pressure).- Parameters:
pressureBara- pressure in bara, or -1 to use inlet pressure
-
setRunChemicalEquilibrium
public void setRunChemicalEquilibrium(boolean enabled) Enables or disables chemical equilibrium calculation.- Parameters:
enabled- true to run equilibrium (default: true)
-
setRunSolidFlash
public void setRunSolidFlash(boolean enabled) Enables or disables solid flash calculation.- Parameters:
enabled- true to run solid flash (default: true)
-
setRunCorrosionAssessment
public void setRunCorrosionAssessment(boolean enabled) Enables or disables corrosion assessment.- Parameters:
enabled- true to run corrosion assessment (default: true)
-
setGibbsMaxIterations
public void setGibbsMaxIterations(int maxIter) Sets Gibbs reactor max iterations.- Parameters:
maxIter- maximum iterations
-
setGibbsDamping
public void setGibbsDamping(double damping) Sets Gibbs reactor damping factor.- Parameters:
damping- damping factor (0-1)
-
setGibbsTolerance
public void setGibbsTolerance(double tolerance) Sets Gibbs reactor convergence tolerance.- Parameters:
tolerance- convergence tolerance
-
setPipeDiameter
public void setPipeDiameter(double diameterM) Sets pipe diameter for blockage risk calculations.- Parameters:
diameterM- pipe inner diameter in metres
-
setPipeSegmentLength
public void setPipeSegmentLength(double lengthM) Sets pipe segment length for blockage risk calculations.- Parameters:
lengthM- pipe segment length in metres
-
setFlowVelocity
public void setFlowVelocity(double velocityMs) Sets gas flow velocity for blockage risk calculations.- Parameters:
velocityMs- gas velocity in m/s
-
setGasFlowRate
public void setGasFlowRate(double flowRateSm3h) Sets gas flow rate at standard conditions for blockage risk calculations.- Parameters:
flowRateSm3h- volumetric flow rate in Sm3/h
-
run
In this method all thermodynamic and unit operations will be calculated in a steady state calculation.
- Parameters:
id- UUID
-
performChemicalEquilibrium
Performs Gibbs free energy minimisation to determine equilibrium products from H2S and O2 reactions at the inlet conditions.- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
setHydrocarbonInert
Marks hydrocarbon components as inert in the Gibbs reactor so they do not participate in reactions.- Parameters:
reactor- the Gibbs reactorsys- the thermo system
-
performSulfurSolubilityAnalysis
Analyses sulfur solubility in the gas phase and checks for solid S8 formation using TP-solid flash at inlet conditions.- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performTemperatureSweep
Sweeps temperature to find the sulfur deposition onset temperature and build a deposition profile. At each temperature, performs a TP-solid flash and records S8 in gas vs solid.- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performCorrosionAssessment
Assesses corrosion risk from sulfur species and CO2. Evaluates:- FeS formation potential from H2S in presence of water
- Sour corrosion severity based on H2S partial pressure (NACE MR0175)
- SO2 corrosion risk and sulfuric acid formation risk
- Direct S8 + Fe corrosion: S8 + 8Fe -> 8FeS
- CO2 corrosion rate via de Waard-Milliams (1991) model
- FeCO3 (siderite) scale formation tendency
- FeS scale morphology (mackinawite / troilite / pyrrhotite)
- Combined CO2 + H2S + S8 quantitative corrosion rate
- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performKineticAnalysis
Performs kinetic analysis of sulfur-related reactions. Evaluates whether reactions are kinetically feasible at the given conditions by comparing reaction half-lives with typical process residence times.Literature-based rate models used:
- H2S thermal oxidation: Ea ~ 50-65 kJ/mol (Monnery et al., 1993; Cheremisinoff, 2000). Negligible below 200 C.
- Claus reaction (catalytic): k = A*exp(-Ea/RT), Ea ~ 30-40 kJ/mol on Al2O3 catalyst
- FeS formation: diffusion-controlled at steel surface, rate depends on H2S partial pressure and temperature. Approximate Arrhenius with Ea ~ 20 kJ/mol (Sun & Nesic, 2009)
- Polysulfane formation: H2S + Sx = H2(S)x+1, intermediate step in sulfur precipitation
- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performSupersaturationAnalysis
Analyses the supersaturation state of dissolved S8 and estimates nucleation risk using classical nucleation theory.The supersaturation ratio sigma = y_S8_actual / y_S8_sat determines whether precipitation will occur:
- sigma < 1: Undersaturated. No deposition risk.
- 1 < sigma < 1.5: Metastable zone. Nucleation unlikely without seed crystals.
- sigma > 1.5: Labile zone. Spontaneous homogeneous nucleation expected.
Literature: Mersmann (2001), Mullin (2001) - Crystallization. The interfacial energy of solid S8 is approx. 0.025-0.035 J/m2.
- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performGasVsLiquidSolubilityComparison
Compares S8 solubility in gas phase versus liquid hydrocarbon phase.S8 is approximately 100-1000x more soluble in liquid hydrocarbons than in the gas phase (Roof, 1971; Roberts, 1997). This has critical implications:
- When liquid HC condenses (crossing hydrocarbon dew point), it acts as a "sulfur sponge" - absorbing S8 from the gas phase and reducing gas-phase supersaturation.
- Conversely, when liquid HC is flashed to gas (e.g., JT valve, separator), S8 that was dissolved in the liquid has nowhere to go - massive S8 precipitation can occur.
- In two-phase (gas + liquid HC) flow, the liquid phase carries most of the dissolved sulfur. Pipeline liquid holdup influences where sulfur deposits.
- Retrograde condensation near the cricondentherm temporarily provides liquid to dissolve S8, but re-vaporisation at lower pressure releases it.
- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
performBlockageRiskAssessment
Assesses the risk of pipeline or equipment blockage from sulfur deposition. Estimates sulfur accumulation rate, time to critical restriction, and identifies pipe sections most vulnerable to plugging.The blockage model considers:
- Sulfur dropout rate from supersaturated gas (kg/h per km)
- Critical accumulation thickness to restrict flow (>5% diameter reduction)
- Flow velocity effect on deposition vs re-entrainment
- Susceptibility of different equipment types to blockage
References: Pack (2005), Wilkes & McMahon (2007) - Sulfur deposition in gas pipelines.
- Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
addEquipmentRisk
private void addEquipmentRisk(List<Map<String, String>> list, String equipment, String riskLevel, String description) Adds an equipment risk entry to the equipment risk list.- Parameters:
list- the risk list to add toequipment- equipment nameriskLevel- risk level stringdescription- risk description
-
performCatalysisAnalysis
Evaluates catalytic pathways for elemental sulfur formation from the gas composition. Analyses homogeneous, heterogeneous, and aqueous-phase catalysis mechanisms based on inlet gas composition and conditions.Literature-based catalysis pathways evaluated:
Catalytic pathways for elemental sulfur formation Pathway Catalyst / Mechanism Conditions Reference Claus reaction: 2H2S + SO2 = 3/8 S8 + 2H2O Al2O3 / TiO2 surface catalyst 200-350 C, Ea ~ 30-40 kJ/mol Monnery et al. (1993) Iron oxide: Fe2O3 + 3H2S = Fe2S3 + 3H2O Pipeline rust, iron sponge Ambient to 60 C, regenerable with O2 Kohl & Nielsen (1997) FeS surface catalysis Corrosion product on steel All pipeline T, heterogeneous Sun & Nesic (2009) Liquid redox: 2Fe3+ + H2S = 2Fe2+ + S + 2H+ Iron chelate (EDTA/NTA) Aqueous, pH 7-9, ambient GPSA (2004) Polysulfide: HS- + (n-1)S = Sn2- + H+ Alkaline aqueous phase pH > 7, water/glycol Kamyshny et al. (2007) COS hydrolysis: COS + H2O = CO2 + H2S Al2O3 catalyst 150-350 C, Ea ~ 35 kJ/mol George (1974) Activated carbon adsorption + catalysis AC surface + O2 traces Ambient, requires O2 traces Bandosz (2002) - Parameters:
inlet- the inlet streampressure- the analysis pressure in bara
-
getComponentMolFrac
Gets the mole fraction of a component from the system, returning 0 if not present.- Parameters:
sys- the thermodynamic systemname- the component name- Returns:
- mole fraction, or 0 if component not found
-
getCatalysisAnalysis
-
getSulfurSolubilityInGas
public double getSulfurSolubilityInGas()Gets the sulfur solubility in the gas phase as mole fraction.- Returns:
- S8 mole fraction in gas at inlet conditions
-
getSulfurSolubilityMgSm3
public double getSulfurSolubilityMgSm3()Gets the sulfur solubility in the gas phase in mg/Sm3.- Returns:
- S8 concentration in mg/Sm3 at standard conditions
-
getSulfurDepositionOnsetTemperature
public double getSulfurDepositionOnsetTemperature()Gets the temperature at which solid sulfur first deposits (in Celsius). Returns NaN if no solid deposition occurs in the sweep range.- Returns:
- onset temperature in Celsius, or NaN
-
isSolidSulfurPresent
public boolean isSolidSulfurPresent()Returns true if solid sulfur is present at inlet conditions.- Returns:
- true if solid S8 phase exists
-
getSolidSulfurFraction
public double getSolidSulfurFraction()Gets the solid sulfur phase fraction at inlet conditions.- Returns:
- solid phase mole fraction
-
hasCorrosionRisk
public boolean hasCorrosionRisk()Returns true if any corrosion risk is identified.- Returns:
- true if FeS, SO2, or H2SO4 corrosion risk exists
-
getEquilibriumComposition
-
getTemperatureSweepResults
-
getCorrosionAssessment
-
getReactionSummary
-
getKineticAnalysis
-
getSupersaturationAnalysis
-
getGasVsLiquidSolubility
-
getBlockageRiskAssessment
-
getResultsAsJson
Returns comprehensive results as a JSON string.- Returns:
- JSON string with all analysis results
-
printSummary
public void printSummary()Prints a human-readable summary of the analysis results to the logger. -
mapToJsonObject
-