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.
 
 
 
 
 
 

154 lines
5.7 KiB

  1. module CProblemDifinition
  2. use CIActionReference
  3. implicit none
  4. public
  5. procedure (ActionInteger), pointer :: Nil => null()
  6. integer, parameter :: Time_ProblemType = 0
  7. integer, parameter :: PumpStrokes_ProblemType = 1
  8. integer, parameter :: VolumePumped_ProblemType = 2
  9. integer, parameter :: DistanceDrilled_ProblemType = 3
  10. integer, parameter :: Clear_StatusType = 0
  11. integer, parameter :: Now_StatusType = 1
  12. integer, parameter :: Later_StatusType = 2
  13. integer, parameter :: Executed_StatusType = 3
  14. type, bind(c), public :: CProblem
  15. integer :: ProblemType
  16. integer :: StatusType
  17. real(8) :: Value
  18. real(8) :: DueValue
  19. end type CProblem
  20. contains
  21. subroutine Execute(problem, action)
  22. type(CProblem), intent(inout) :: problem
  23. procedure (ActionInteger), pointer, intent(in) :: action
  24. problem%StatusType = Executed_StatusType
  25. if(problem%StatusType == Executed_StatusType .and. associated(action)) call action(Executed_StatusType)
  26. end subroutine
  27. type(CProblem) function SetDue(problem, action)
  28. use CSimulationVariables
  29. implicit none
  30. type(CProblem), intent(in) :: problem
  31. procedure (ActionInteger), pointer, intent(in) :: action
  32. real(8) :: CurrentTime
  33. real(8) :: CurrentPumpStrokes
  34. real(8) :: CurrentVolumePumped
  35. real(8) :: CurrentDistanceDrilled
  36. real(8) :: Due
  37. CurrentTime = 0
  38. CurrentPumpStrokes = 0
  39. CurrentVolumePumped = 0
  40. CurrentDistanceDrilled = 0
  41. SetDue = problem
  42. if(problem%StatusType == Clear_StatusType .and. associated(action)) then
  43. call action(Clear_StatusType)
  44. SetDue%DueValue = 0
  45. return
  46. endif
  47. select case (problem%ProblemType)
  48. case(Time_ProblemType)
  49. select case (SimulationState)
  50. case(SimulationState_Stopped)
  51. CurrentTime = 0
  52. case(SimulationState_Started)
  53. CurrentTime = dble(SimulationTime)
  54. case(SimulationState_Paused)
  55. CurrentTime = dble(SimulationTime)
  56. end select
  57. Due = problem%Value + CurrentTime
  58. case(PumpStrokes_ProblemType)
  59. select case (SimulationState)
  60. case(SimulationState_Stopped)
  61. CurrentPumpStrokes = 0
  62. case(SimulationState_Started)
  63. CurrentPumpStrokes = TotalPumpStrokes
  64. case(SimulationState_Paused)
  65. CurrentPumpStrokes = TotalPumpStrokes
  66. end select
  67. Due = problem%Value + CurrentPumpStrokes
  68. case(VolumePumped_ProblemType)
  69. select case (SimulationState)
  70. case(SimulationState_Stopped)
  71. CurrentVolumePumped = 0
  72. case(SimulationState_Started)
  73. CurrentVolumePumped = TotalVolumePumped
  74. case(SimulationState_Paused)
  75. CurrentVolumePumped = TotalVolumePumped
  76. end select
  77. Due = problem%Value + CurrentVolumePumped
  78. case(DistanceDrilled_ProblemType)
  79. select case (SimulationState)
  80. case(SimulationState_Stopped)
  81. CurrentDistanceDrilled = 0
  82. case(SimulationState_Started)
  83. CurrentDistanceDrilled = DistanceDrilled
  84. case(SimulationState_Paused)
  85. CurrentDistanceDrilled = DistanceDrilled
  86. end select
  87. Due = problem%Value + CurrentDistanceDrilled
  88. end select
  89. SetDue%DueValue = Due
  90. end function SetDue
  91. subroutine ProcessDueTime(problem, action, time)
  92. use CSimulationVariables
  93. use CLog3
  94. implicit none
  95. type(CProblem) :: problem
  96. procedure (ActionInteger), pointer, intent(in) :: action
  97. integer :: time
  98. if(problem%ProblemType == Time_ProblemType .and. problem%StatusType /= Executed_StatusType .and. problem%StatusType /= Clear_StatusType) then
  99. if(time >= int(problem%DueValue)) call Execute(problem, action)
  100. end if
  101. end subroutine
  102. subroutine ProcessDuePumpStrokes(problem, action, strokes)
  103. use CSimulationVariables
  104. implicit none
  105. type(CProblem) :: problem
  106. procedure (ActionInteger), pointer, intent(in) :: action
  107. integer :: strokes
  108. if(problem%ProblemType == PumpStrokes_ProblemType .and. problem%StatusType /= Executed_StatusType .and. problem%StatusType /= Clear_StatusType) then
  109. if(strokes >= int(problem%DueValue)) call Execute(problem, action)
  110. end if
  111. end subroutine
  112. subroutine ProcessDueVolumePumped(problem, action, volume)
  113. use CSimulationVariables
  114. implicit none
  115. type(CProblem) :: problem
  116. procedure (ActionInteger), pointer, intent(in) :: action
  117. real(8) :: volume
  118. if(problem%ProblemType == VolumePumped_ProblemType .and. problem%StatusType /= Executed_StatusType .and. problem%StatusType /= Clear_StatusType) then
  119. if(volume >= problem%DueValue) call Execute(problem, action)
  120. end if
  121. end subroutine
  122. subroutine ProcessDueDistanceDrilled(problem, action, distance)
  123. use CSimulationVariables
  124. implicit none
  125. type(CProblem) :: problem
  126. procedure (ActionInteger), pointer, intent(in) :: action
  127. real(8) :: distance
  128. if(problem%ProblemType == DistanceDrilled_ProblemType .and. problem%StatusType /= Executed_StatusType .and. problem%StatusType /= Clear_StatusType) then
  129. if(distance >= problem%DueValue) call Execute(problem, action)
  130. end if
  131. end subroutine
  132. end module CProblemDifinition