Simulation Core
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

Annulus_and_Openhole_Pressure_Distribution.i90 17 KiB

1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282
  1. # 1 "/mnt/c/Projects/VSIM/SimulationCore2/FluidFlow/Annulus_and_Openhole_Pressure_Distribution.f90"
  2. SUBROUTINE PressureAnnAndOHDistribution
  3. !! Record of revisions
  4. !! Date Programmer Discription of change
  5. !! ------ ------------ -----------------------
  6. !! 1396/07/30 Sheikh Original code
  7. !!
  8. USE FricPressDropVarsModule
  9. USE MudSystemVARIABLES
  10. use SimulationVariables !@@@
  11. use PressureDisplayVARIABLESModule
  12. USE GeoElements_FluidModule
  13. USE Fluid_Flow_Startup_Vars
  14. use KickVARIABLESModule
  15. USE CMudPropertiesVariables
  16. use SimulationVariables !@
  17. USE CReservoirVariables
  18. use MudSystemModule
  19. USE CHOKEVARIABLES
  20. use SimulationVariables !@
  21. use CChokeManifoldVariables
  22. use SimulationVariables
  23. use SimulationVariables
  24. USE CError
  25. USE , INTRINSIC :: IEEE_ARITHMETIC
  26. IMPLICIT NONE
  27. INTEGER :: i , j , k , l
  28. INTEGER :: ifric
  29. REAL :: Fraction
  30. data%State%FricPressDrop%KBOP = 0.0
  31. IF (WellHeadOpen .OR. NoGasPocket == 0) THEN !! (mud circulation is normal wellhead may be open or closed) OR (kick is in the well and well head is open)
  32. !!!!! Determining flow rate in each section
  33. i = data%State%FricPressDrop%AnnulusFirstEl
  34. j = data%State%FricPressDrop%OpenholeFirstEl - 1
  35. !!!!!!!!!!!!!!!!!!!!!!!!! flowrates due to external sources like pump and tripping
  36. FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = (ClingingFactor * FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%Area + FlowEl(data%State%FricPressDrop%StringFirstEl)%Area) * DrillStringSpeed * ConvMintoSec * Convft3toUSgal ! flowrate in annulus due to tripping
  37. FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate + REAL(data%State%MudSystem%MudVolume_InjectedToBH) * ConvMintoSec / dt ! flowrate in annulus due to pump
  38. IF (data%State%MudSystem%ShoeFractured) THEN ! reduction of flowrate due to formation fracture and lost circulation
  39. IF (ShoeFlowElNo > data%State%FricPressDrop%AnnulusLastEl) THEN ! shoe is in openhole
  40. FlowEl(ShoeFlowElNo : data%State%FricPressDrop%NumbEl)%FlowRate = - data%State%MudSystem%Qlost
  41. FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate - data%State%MudSystem%Qlost
  42. ELSE ! shoe is in annulus
  43. FlowEl(ShoeFlowElNo : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = FlowEl(ShoeFlowElNo : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate - data%State%MudSystem%Qlost
  44. END IF
  45. END IF
  46. !!!!!!!!!!!!!!!!!!!!!!!!!
  47. !!!!!!!!!!!!!!!!!!!!!!!!! initial guess flowrates for opening BOP or choke line
  48. IF (WellHeadWasOpen == .FALSE. .AND. NoGasPocket > 0 .AND. KickIteration == 1) THEN
  49. IF (ChokeKroneckerDelta == 1) THEN ! flow on choke line
  50. IF (data%State%FricPressDrop%TotalOpenChokeArea < 0.01 * data%State%Choke%ChokeAreaFullyOpen) THEN
  51. WRITE (*,*) 'density , TotalOpenChokeArea' , "data%Equipments%DownHole%Density", data%State%FricPressDrop%TotalOpenChokeArea
  52. data%State%FricPressDrop%TotalOpenChokeArea = 0.01 * data%State%Choke%ChokeAreaFullyOpen
  53. END IF
  54. data%State%FricPressDrop%Kchoke = (ChokeDensity / ((2.0 * 89158.0) * (0.26 * 0.61 * data%State%FricPressDrop%TotalOpenChokeArea)**2)) * 4.0 ! *4.d0: seyyed gofte
  55. GasPocketFlowInduced%Array(:) = MIN((0.6 / NoGasPocket * SQRT(data%State%PressureDisplay%PressureGauges(2) / data%State%FricPressDrop%Kchoke)) , (0.05 * GasPocketNewVol%Array(:) * ConvFt3toUSgal / 60 / dt))
  56. WRITE (*,*) ' PressureGauges(2) , Kchoke' , data%State%PressureDisplay%PressureGauges(2) , data%State%FricPressDrop%Kchoke
  57. WRITE (*,*) 'Initial guess after opening choke =', GasPocketFlowInduced%Array(1)
  58. WRITE (*,*) ' valve 49 ', Manifold%Valve(49)%Status
  59. WRITE (*,*) ' valve 47 ', Manifold%Valve(47)%Status
  60. WRITE (*,*) ' valve 26 ', Manifold%Valve(26)%Status
  61. WRITE (*,*) ' valve 30 ', Manifold%Valve(30)%Status
  62. WRITE (*,*) ' valve 34 ', Manifold%Valve(34)%Status
  63. WRITE (*,*) ' valve 63 ', Manifold%Valve(63)%Status
  64. WRITE (*,*) ' valve 28 ', Manifold%Valve(28)%Status
  65. WRITE (*,*) ' valve 33 ', Manifold%Valve(33)%Status
  66. WRITE (*,*) ' valve 62 ', Manifold%Valve(62)%Status
  67. WRITE (*,*) ' valve 36 ', Manifold%Valve(36)%Status
  68. WRITE (*,*) ' valve 38 ', Manifold%Valve(38)%Status
  69. ELSE ! flow through bell nipple
  70. k = data%State%FricPressDrop%NoHorizontalEl + data%State%FricPressDrop%NoStringEl + data%State%FricPressDrop%NoAnnulusEl
  71. data%State%FricPressDrop%KBOP = FlowEl(data%State%FricPressDrop%AnnulusLastEl)%Density / ((2.0 * 89158.0) * (0.26 * 0.61 * data%State%ShearRAM%MinimumOpenArea_InBOP)**2)
  72. GasPocketFlowInduced%Array(:) = MIN((0.1 / NoGasPocket * SQRT(data%State%PressureDisplay%PressureGauges(6) / data%State%FricPressDrop%KBOP)) , (0.05 * GasPocketNewVol%Array(:) * ConvFt3toUSgal / 60 / dt))
  73. WRITE (*,*) 'PressureGauges(6), KBOP', data%State%PressureDisplay%PressureGauges(6), data%State%FricPressDrop%KBOP
  74. WRITE (*,*) 'Initial guess after opening BOP =', GasPocketFlowInduced%Array(1)
  75. END IF
  76. END IF
  77. !!!!!!!!!!!!!!!!!!!!!!!!!
  78. !!!!!!!!!!!!!!!!!!!!!!!!! flowrates due to expansion of gas pockets or kick influx
  79. !i = AnnulusFirstEl
  80. !j = OpenholeFirstEl - 1
  81. IF (NoGasPocket > 0) THEN
  82. DO l = 1 , NoGasPocket !GasPocketFlowEl
  83. k = GasPocketFlowEl(l , 1)
  84. !WRITE (*,*) 'GasPocketFlowEl(l , 1)', l, k, j
  85. IF (k == 0) CALL ERRORSTOP('GasPocketFlowEl(l , 1) == 0', l)
  86. IF (k >= data%State%FricPressDrop%OpenholeFirstEl) THEN ! gas pocket is in open hole only
  87. FlowEl(k : data%State%FricPressDrop%NumbEl)%FlowRate = FlowEl(k : data%State%FricPressDrop%NumbEl)%FlowRate + GasPocketFlowInduced%Array(l) ! openhole elements above pocket
  88. FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = FlowEl(data%State%FricPressDrop%AnnulusFirstEl : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate + GasPocketFlowInduced%Array(l) ! annulus and choke line elements
  89. ELSE IF (k < data%State%FricPressDrop%OpenholeFirstEl) THEN ! gas pocket is in annulus ond/or choke line only
  90. FlowEl(k : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = FlowEl(k : data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate + GasPocketFlowInduced%Array(l) ! annulus or choke line elements above pocket
  91. END IF
  92. END DO
  93. END IF
  94. !!!!!!!!!!!!!!!!!!!!!!!!!
  95. !!!!! END - Determining flow rate in each section
  96. !!!!!!!!!!!!!!!!!!!!!!!!! effect of surge and swab on frictional pressure drop direction
  97. DO l = data%State%FricPressDrop%AnnulusFirstEl , data%State%FricPressDrop%OpenholeFirstEl - 1
  98. IF (FlowEl(l)%FlowRate < 0.0) THEN
  99. FlowEl(l)%FrictionDirection = -1
  100. IF (FlowEl(l)%FlowRate > -1.0 * PressFlowrateTolerance .AND. ALLOCATED(GasPocketWeight%Array)) FlowEl(l)%FlowRate = - PressFlowrateTolerance
  101. ELSE
  102. FlowEl(l)%FrictionDirection = 1
  103. IF (FlowEl(l)%FlowRate < PressFlowrateTolerance .AND. ALLOCATED(GasPocketWeight%Array)) FlowEl(l)%FlowRate = PressFlowrateTolerance
  104. END IF
  105. END DO
  106. !!!!!!!!!!!!!!!!!!!!!!!!!
  107. !!!!!!!!!!!!!!!!!!!!!!!!! Calculating Back Pressure, in well to pit path back pressure = 0
  108. ! in well to choke manifold path back pressure is equal to pressure before choke not casing pressure
  109. IF (ChokeKroneckerDelta == 1) THEN
  110. IF (FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate < 0.0) THEN
  111. WRITE (*,*) ' Negative choke flowrate'
  112. FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate = MAX((REAL(data%State%MudSystem%MudVolume_InjectedToBH) * ConvMintoSec / dt) , 10.0)
  113. END IF
  114. data%State%MudSystem%deltaPchoke = (data%State%FricPressDrop%Kchoke * FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate * ABS(FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%FlowRate)) * 1.d0
  115. IF (data%State%MudSystem%deltaPchoke < 0.d0) data%State%MudSystem%deltaPchoke = 0.d0
  116. data%State%FricPressDrop%BackPressure = REAL(data%State%MudSystem%deltaPchoke)
  117. ELSE
  118. data%State%FricPressDrop%BackPressure = 0.0
  119. END IF
  120. IF (IEEE_IS_NaN(data%State%FricPressDrop%BackPressure)) CALL ErrorStop('NaN in calculating back pressure' , FlowEl(j)%FlowRate)
  121. !write(*,*) 'BackPressure=' , BackPressure
  122. !!!!!!!!!!!!!!!!!!!!!!!!! when flow passes through choke manifold, solution process may be unstable
  123. IF (ChokeKroneckerDelta == 1) THEN ! thus we should stabilize solution
  124. IF (data%State%FricPressDrop%TotalOpenChokeArea > 0.5 * data%State%Choke%ChokeAreaFullyOpen) THEN
  125. KickCorrectionUnderRelaxation = 0.6
  126. ELSE IF (data%State%FricPressDrop%TotalOpenChokeArea > 0.1 * data%State%Choke%ChokeAreaFullyOpen) THEN
  127. KickCorrectionUnderRelaxation = 0.5
  128. ELSE ! TotalOpenChokeArea < 0.1 * ChokeAreaFullyOpen
  129. KickCorrectionUnderRelaxation = 0.4
  130. END IF
  131. ELSE
  132. KickCorrectionUnderRelaxation = 0.6
  133. END IF
  134. !!!!!!!!!!!!!!!!!!!!!!!!!
  135. !!!!!!!!!!!!!!!!!!!!!!!!! calculating frictional pressure drop in annulus, chooke line and open hole elements
  136. DO ifric = data%State%FricPressDrop%AnnulusFirstEl , data%State%FricPressDrop%NumbEl
  137. CALL FricPressDrop(ifric)
  138. !WRITE (*,*) ' element No, FlowRate , Density, FricPressLoss', ifric, FlowEl(ifric)%FlowRate, FlowEl(ifric)%Density, FlowEl(ifric)%FricPressLoss
  139. IF (IEEE_IS_NaN(FlowEl(ifric)%FricPressLoss)) THEN
  140. WRITE (*,*) 'H, S, A, Ch, O', data%State%FricPressDrop%NoHorizontalEl , data%State%FricPressDrop%NoStringEl , data%State%FricPressDrop%NoAnnulusEl , data%State%FricPressDrop%NoWellToChokeEl , data%State%FricPressDrop%NoOpenHoleEl
  141. WRITE (*,*) 'Ann/Op start, end, density, Q, mu, Type' , FlowEl(ifric)%StartX, FlowEl(ifric)%EndX, FlowEl(ifric)%Density, FlowEl(ifric)%FlowRate, FlowEl(ifric)%mueff, FlowEl(ifric)%MaterialType
  142. CALL ErrorStop('NaN in calculating pressure drop' , ifric)
  143. END IF
  144. END DO
  145. !!!!!!!!!!!!!!!!!!!!!!!!! Pressure distribution in annulus
  146. j = data%State%FricPressDrop%OpenholeFirstEl - 1
  147. FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%EndPress = data%State%FricPressDrop%BackPressure
  148. FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%StartPress = FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%EndPress + FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%FricPressLoss + FlowEl(data%State%FricPressDrop%OpenholeFirstEl - 1)%StaticPressDiff
  149. DO l = data%State%FricPressDrop%OpenholeFirstEl - 2 , data%State%FricPressDrop%AnnulusFirstEl , -1
  150. !WRITE (*,*) '123'
  151. FlowEl(l)%EndPress = FlowEl(l + 1)%StartPress
  152. FlowEl(l)%StartPress = FlowEl(l)%EndPress + FlowEl(l)%FricPressLoss + FlowEl(l)%StaticPressDiff
  153. END DO
  154. !!!!!!!!!!!!!!!!! Pressure distribution in Open Hole
  155. FlowEl(data%State%FricPressDrop%NumbEl)%EndPress = FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%StartPress
  156. FlowEl(data%State%FricPressDrop%NumbEl)%StartPress = FlowEl(data%State%FricPressDrop%NumbEl)%EndPress + FlowEl(data%State%FricPressDrop%NumbEl)%FricPressLoss + FlowEl(data%State%FricPressDrop%NumbEl)%StaticPressDiff
  157. DO l = data%State%FricPressDrop%NumbEl - 1 , data%State%FricPressDrop%OpenholeFirstEl , -1
  158. !WRITE(*,*) ' ope'
  159. FlowEl(l)%EndPress = FlowEl(l + 1)%StartPress
  160. FlowEl(l)%StartPress = FlowEl(l)%EndPress + FlowEl(l)%FricPressLoss + FlowEl(l)%StaticPressDiff
  161. !WRITE (*,*) ' Length, static, frictional open' , FlowEl(i)%Length, FlowEl(i)%StaticPressDiff, FlowEl(i)%FricPressLoss
  162. !END IF
  163. END DO
  164. ELSE ! wellhead is closed and kick is in the well
  165. !WRITE (*,*) ' well head is closed'
  166. k = GasPocketFlowEl(NoGasPocket , 1)
  167. !WRITE (*,*) 'k, Pocket Press', k, GasPocketOldPress%Array(NoGasPocket) - StandardPress
  168. i = data%State%FricPressDrop%AnnulusFirstEl
  169. j = data%State%FricPressDrop%OpenholeFirstEl - 1
  170. FlowEl(k)%StartPress = GasPocketOldPress%Array(NoGasPocket) - StandardPress
  171. FlowEl(k)%EndPress = GasPocketOldPress%Array(NoGasPocket) - StandardPress
  172. IF (k > data%State%FricPressDrop%OpenholeFirstEl - 1) THEN ! Top pocket StartX is in Open hole
  173. !WRITE (*,*) 'here 1'
  174. DO l = k - 1 , data%State%FricPressDrop%OpenholeFirstEl , -1 ! below elements in openhole
  175. !WRITE (*,*) 'here 1-1'
  176. FlowEl(l)%EndPress = FlowEl(l + 1)%StartPress
  177. FlowEl(l)%StartPress = FlowEl(l)%EndPress + FlowEl(l)%StaticPressDiff
  178. END DO
  179. DO l = k + 1 , data%State%FricPressDrop%NumbEl ! Above elements in openhole
  180. !WRITE (*,*) 'here 1-2'
  181. FlowEl(l)%StartPress = FlowEl(l - 1)%EndPress
  182. FlowEl(l)%EndPress = FlowEl(l)%StartPress - FlowEl(l)%StaticPressDiff
  183. END DO
  184. FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%StartPress = FlowEl(data%State%FricPressDrop%NumbEl)%EndPress
  185. FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%EndPress = FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%StartPress - FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%StaticPressDiff
  186. DO l = data%State%FricPressDrop%AnnulusFirstEl + 1 , data%State%FricPressDrop%OpenholeFirstEl - 1
  187. FlowEl(l)%StartPress = FlowEl(l - 1)%EndPress
  188. FlowEl(l)%EndPress = FlowEl(l)%StartPress - FlowEl(l)%StaticPressDiff
  189. END DO
  190. ELSE ! Top pocket StartX is in annulus or choke line
  191. DO l = k - 1 , data%State%FricPressDrop%AnnulusFirstEl , -1 ! below elements in annnulus
  192. FlowEl(l)%EndPress = FlowEl(l + 1)%StartPress
  193. FlowEl(l)%StartPress = FlowEl(l)%EndPress + FlowEl(l)%StaticPressDiff
  194. END DO
  195. DO l = k + 1 , data%State%FricPressDrop%OpenholeFirstEl - 1 ! Above elements in annulus
  196. FlowEl(l)%StartPress = FlowEl(l - 1)%EndPress
  197. FlowEl(l)%EndPress = FlowEl(l)%StartPress - FlowEl(l)%StaticPressDiff
  198. END DO
  199. FlowEl(data%State%FricPressDrop%NumbEl)%EndPress = FlowEl(data%State%FricPressDrop%AnnulusFirstEl)%StartPress
  200. FlowEl(data%State%FricPressDrop%NumbEl)%StartPress = FlowEl(data%State%FricPressDrop%NumbEl)%EndPress + FlowEl(data%State%FricPressDrop%NumbEl)%StaticPressDiff
  201. DO l = data%State%FricPressDrop%NumbEl - 1 , data%State%FricPressDrop%OpenholeFirstEl , -1
  202. FlowEl(l)%EndPress = FlowEl(l + 1)%StartPress
  203. FlowEl(l)%StartPress = FlowEl(l)%EndPress + FlowEl(l)%StaticPressDiff
  204. END DO
  205. END IF
  206. END IF
  207. !!!!!!!!!!!!!!!!!!!!!! checking pressure for preventing NaN in pressures
  208. DO l = data%State%FricPressDrop%OpenholeFirstEl - 1 , data%State%FricPressDrop%AnnulusFirstEl , -1 ! annulus or choke elements
  209. !WRITE (*,*) 'start, end' , FlowEl(i)%StartX, FlowEl(i)%EndX
  210. IF (IEEE_IS_NaN(FlowEl(l)%EndPress)) THEN
  211. WRITE (*,*) 'H, S, A, Ch, O', data%State%FricPressDrop%NoHorizontalEl , data%State%FricPressDrop%NoStringEl , data%State%FricPressDrop%NoAnnulusEl , data%State%FricPressDrop%NoWellToChokeEl , data%State%FricPressDrop%NoOpenHoleEl
  212. WRITE (*,*) 'Ann/Ch start, end, density, Q, mu' , FlowEl(l)%StartX, FlowEl(l)%EndX, FlowEl(l)%Density, FlowEl(l)%FlowRate, FlowEl(l)%mueff, FlowEl(l)%MaterialType
  213. CALL ERRORSTOP('NaN in EndPress', l)
  214. END IF
  215. END DO
  216. DO l = data%State%FricPressDrop%NumbEl , data%State%FricPressDrop%OpenholeFirstEl - 1 , -1 ! op elements
  217. !WRITE (*,*) 'start, end' , FlowEl(i)%StartX, FlowEl(i)%EndX
  218. IF (IEEE_IS_NaN(FlowEl(l)%EndPress)) THEN
  219. WRITE (*,*) 'H, S, A, Ch, O', data%State%FricPressDrop%NoHorizontalEl , data%State%FricPressDrop%NoStringEl , data%State%FricPressDrop%NoAnnulusEl , data%State%FricPressDrop%NoWellToChokeEl , data%State%FricPressDrop%NoOpenHoleEl
  220. WRITE (*,*) 'Op start, end, density, Q, mu' , FlowEl(l)%StartX, FlowEl(l)%EndX, FlowEl(l)%Density, FlowEl(l)%FlowRate, FlowEl(l)%mueff, FlowEl(l)%MaterialType
  221. CALL ERRORSTOP('NaN in EndPress', l)
  222. END IF
  223. END DO
  224. !!!!!!!!!!!!!!!!!!!!!!
  225. !!!!!!!!!!!!!!!!!!!!!!
  226. BottomHolePress = FlowEl(data%State%FricPressDrop%OpenholeFirstEl)%StartPress
  227. !!!!!!!!!!!!!!!!!!!!!!
  228. END SUBROUTINE