genecrmod 0.0.0 → 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/VERSION +1 -1
- data/genecrmod.gemspec +72 -0
- data/lib/genecrmod/gene.rb +289 -0
- data/lib/genecrmod/namelists.rb +3723 -0
- data/lib/genecrmod.rb +1 -0
- data/sync_variables/helper.rb +18 -0
- data/sync_variables/sync_variables.rb +7 -0
- metadata +6 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 7d5f9bda05b63e6c3894ce02d9213099a0485f67
|
|
4
|
+
data.tar.gz: c195fa1c85c1f468fc29edbfbce7819a3236940d
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: f9b2d1526aca46eecd3dcf136fa1fdc9cd61bffb76cfe12cc745d0dc85d09b01f6dcc863c2316182995ea31411d5846d35211cb6a14f27f83a765a99ce6cdeba
|
|
7
|
+
data.tar.gz: 625ce2f319afa5fb27edb34aef9ebfc6cfef5a6b0e1c0bdc1739d7f3b27e4bfba7c4984f4abc5d97ea90b11b4d0cb28adda9fe832f4b24ae2d603c7df0ed7ed1
|
data/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
0.
|
|
1
|
+
0.1.0
|
data/genecrmod.gemspec
ADDED
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
# Generated by jeweler
|
|
2
|
+
# DO NOT EDIT THIS FILE DIRECTLY
|
|
3
|
+
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
|
4
|
+
# -*- encoding: utf-8 -*-
|
|
5
|
+
# stub: genecrmod 0.1.0 ruby lib
|
|
6
|
+
|
|
7
|
+
Gem::Specification.new do |s|
|
|
8
|
+
s.name = "genecrmod"
|
|
9
|
+
s.version = "0.1.0"
|
|
10
|
+
|
|
11
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
|
12
|
+
s.require_paths = ["lib"]
|
|
13
|
+
s.authors = ["Edmund Highcock"]
|
|
14
|
+
s.date = "2014-07-17"
|
|
15
|
+
s.description = "A module which allows the GENE gyrokinetic code to be run using the CodeRunner framework. "
|
|
16
|
+
s.email = "edmundhighcock@users.sourceforge.net"
|
|
17
|
+
s.extra_rdoc_files = [
|
|
18
|
+
"LICENSE.txt",
|
|
19
|
+
"README.rdoc"
|
|
20
|
+
]
|
|
21
|
+
s.files = [
|
|
22
|
+
".document",
|
|
23
|
+
"Gemfile",
|
|
24
|
+
"LICENSE.txt",
|
|
25
|
+
"README.rdoc",
|
|
26
|
+
"Rakefile",
|
|
27
|
+
"VERSION",
|
|
28
|
+
"genecrmod.gemspec",
|
|
29
|
+
"lib/genecrmod.rb",
|
|
30
|
+
"lib/genecrmod/gene.rb",
|
|
31
|
+
"lib/genecrmod/namelists.rb",
|
|
32
|
+
"sync_variables/helper.rb",
|
|
33
|
+
"sync_variables/sync_variables.rb",
|
|
34
|
+
"test/helper.rb",
|
|
35
|
+
"test/test_genecrmod.rb"
|
|
36
|
+
]
|
|
37
|
+
s.homepage = "http://github.com/edmundhighcock/genecrmod"
|
|
38
|
+
s.licenses = ["GPLv3"]
|
|
39
|
+
s.rubygems_version = "2.2.2"
|
|
40
|
+
s.summary = "A module which allows the GENE gyrokinetic code to be run using the CodeRunner framework."
|
|
41
|
+
|
|
42
|
+
if s.respond_to? :specification_version then
|
|
43
|
+
s.specification_version = 4
|
|
44
|
+
|
|
45
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
|
46
|
+
s.add_runtime_dependency(%q<coderunner>, [">= 0.14.2"])
|
|
47
|
+
s.add_development_dependency(%q<shoulda>, ["= 3.0.1"])
|
|
48
|
+
s.add_development_dependency(%q<rdoc>, ["~> 3.12"])
|
|
49
|
+
s.add_development_dependency(%q<bundler>, ["~> 1.0"])
|
|
50
|
+
s.add_development_dependency(%q<jeweler>, ["~> 2.0.1"])
|
|
51
|
+
s.add_development_dependency(%q<simplecov>, [">= 0"])
|
|
52
|
+
s.add_development_dependency(%q<minitest>, ["~> 4"])
|
|
53
|
+
else
|
|
54
|
+
s.add_dependency(%q<coderunner>, [">= 0.14.2"])
|
|
55
|
+
s.add_dependency(%q<shoulda>, ["= 3.0.1"])
|
|
56
|
+
s.add_dependency(%q<rdoc>, ["~> 3.12"])
|
|
57
|
+
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
|
58
|
+
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
|
59
|
+
s.add_dependency(%q<simplecov>, [">= 0"])
|
|
60
|
+
s.add_dependency(%q<minitest>, ["~> 4"])
|
|
61
|
+
end
|
|
62
|
+
else
|
|
63
|
+
s.add_dependency(%q<coderunner>, [">= 0.14.2"])
|
|
64
|
+
s.add_dependency(%q<shoulda>, ["= 3.0.1"])
|
|
65
|
+
s.add_dependency(%q<rdoc>, ["~> 3.12"])
|
|
66
|
+
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
|
67
|
+
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
|
68
|
+
s.add_dependency(%q<simplecov>, [">= 0"])
|
|
69
|
+
s.add_dependency(%q<minitest>, ["~> 4"])
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
|
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
|
|
2
|
+
class CodeRunner
|
|
3
|
+
# This is a customised subclass of the CodeRunner::Run class which allows CodeRunner to run and analyse the GENE gyrokinetic code (see http://www2.ipp.mpg.de/~fsj/gene/)
|
|
4
|
+
#
|
|
5
|
+
#p 'hellllllooooo!!!'
|
|
6
|
+
class Gene < Run::FortranNamelist
|
|
7
|
+
#include CodeRunner::SYSTEM_MODULE
|
|
8
|
+
#
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
# Where this file is
|
|
14
|
+
@code_module_folder = File.dirname(File.expand_path(__FILE__)) # i.e. the directory this file is in
|
|
15
|
+
|
|
16
|
+
# Use the Run::FortranNamelist tools to process the variable database
|
|
17
|
+
setup_namelists(@code_module_folder)
|
|
18
|
+
|
|
19
|
+
# Setup gs2 in case people are using it
|
|
20
|
+
|
|
21
|
+
################################################
|
|
22
|
+
# Quantities that are read or determined by CodeRunner
|
|
23
|
+
# after the simulation has ended
|
|
24
|
+
###################################################
|
|
25
|
+
|
|
26
|
+
@results = [
|
|
27
|
+
]
|
|
28
|
+
|
|
29
|
+
@code_long="GENE Gyrokinetic Electromagnetic Numerical Experiment"
|
|
30
|
+
|
|
31
|
+
@run_info=[:time, :is_a_restart, :restart_id, :restart_run_name, :completed_timesteps, :percent_complete]
|
|
32
|
+
|
|
33
|
+
@uses_mpi = true
|
|
34
|
+
|
|
35
|
+
@modlet_required = false
|
|
36
|
+
|
|
37
|
+
@naming_pars = []
|
|
38
|
+
|
|
39
|
+
# Any folders which are a number will contain the results from flux simulations.
|
|
40
|
+
@excluded_sub_folders = []
|
|
41
|
+
|
|
42
|
+
# A hook which gets called when printing the standard run information to the screen using the status command.
|
|
43
|
+
def print_out_line
|
|
44
|
+
#p ['id', id, 'ctd', ctd]
|
|
45
|
+
#p rcp.results.zip(rcp.results.map{|r| send(r)})
|
|
46
|
+
name = @run_name
|
|
47
|
+
name += " (res: #@restart_id)" if @restart_id
|
|
48
|
+
name += " real_id: #@real_id" if @real_id
|
|
49
|
+
beginning = sprintf("%2d:%d %-60s %1s:%2.1f(%s) %3s%1s", @id, @job_no, name, @status.to_s[0,1], @run_time.to_f / 60.0, @nprocs.to_s, percent_complete, "%")
|
|
50
|
+
if ctd
|
|
51
|
+
#beginning += sprintf("Q:%f, Pfusion:%f MW, Ti0:%f keV, Te0:%f keV, n0:%f x10^20", fusionQ, pfus, ti0, te0, ne0)
|
|
52
|
+
end
|
|
53
|
+
beginning += " ---#{@comment}" if @comment
|
|
54
|
+
beginning
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
# Modify new_run so that it becomes a restart of self. Adusts
|
|
60
|
+
# all the parameters of the new run to be equal to the parameters
|
|
61
|
+
# of the run that calls this function, and sets up its run name
|
|
62
|
+
# correctly
|
|
63
|
+
def restart(new_run)
|
|
64
|
+
raise "Restart not tested yet"
|
|
65
|
+
#new_run = self.dup
|
|
66
|
+
(rcp.variables).each{|v| new_run.set(v, send(v)) if send(v)}
|
|
67
|
+
#if @flux_option == "gs2"
|
|
68
|
+
#gs2_runs.each_with_index do |run, i|
|
|
69
|
+
#CodeRunner::Gs2.rcp.variables.each{|v| new_run.gs2_runs[i].set(v, run.send(v)) if run.send(v)}
|
|
70
|
+
#end
|
|
71
|
+
#end
|
|
72
|
+
#@naming_pars.delete(:preamble)
|
|
73
|
+
#SUBMIT_OPTIONS.each{|v| new_run.set(v, self.send(v)) unless new_run.send(v)}
|
|
74
|
+
##(rcp.results + rcp.gs2_run_info).each{|result| new_run.set(result, nil)}
|
|
75
|
+
new_run.is_a_restart = true
|
|
76
|
+
new_run.restart_id = @id
|
|
77
|
+
new_run.restart_run_name = @run_name
|
|
78
|
+
new_run.nopt = -1
|
|
79
|
+
#new_run.init_option = "restart"
|
|
80
|
+
#new_run.iternt_file = @run_name + ".iternt"
|
|
81
|
+
#new_run.iterflx_file = @run_name + ".iterflx"
|
|
82
|
+
#new_run.init_file = @run_name + ".tmp"
|
|
83
|
+
#@runner.nprocs = @nprocs if @runner.nprocs == "1" # 1 is the default so this means the user probably didn't specify nprocs
|
|
84
|
+
#raise "Restart must be on the same number of processors as the previous run: new is #{new_run.nprocs.inspect} and old is #{@nprocs.inspect}" if !new_run.nprocs or new_run.nprocs != @nprocs
|
|
85
|
+
### @runner.parameters.each{|var, value| new_run.set(var,value)} if @runner.parameters
|
|
86
|
+
### ep @runner.parameters
|
|
87
|
+
new_run.run_name = nil
|
|
88
|
+
new_run.naming_pars = @naming_pars
|
|
89
|
+
new_run.update_submission_parameters(new_run.parameter_hash.inspect, false) if new_run.parameter_hash
|
|
90
|
+
new_run.naming_pars.delete(:restart_id)
|
|
91
|
+
new_run.generate_run_name
|
|
92
|
+
#new_run.run_name += '_t'
|
|
93
|
+
eputs 'Copying GENE Restart file'
|
|
94
|
+
##system "ls #@directory"
|
|
95
|
+
FileUtils.cp("#@directory/NOUT", "#{new_run.directory}/NIN")
|
|
96
|
+
##########if new_run.flux_option == "gs2" and @flux_option == "gs2"
|
|
97
|
+
##########for i in 0...n_flux_tubes
|
|
98
|
+
##########new_run.gs2_runs[i].directory = new_run.directory + "/flux_tube_#{i+1}"
|
|
99
|
+
##########FileUtils.makedirs(new_run.gs2_runs[i].directory)
|
|
100
|
+
###########ep ['gs2_runs[i] before', gs2_runs[i].nwrite, new_run.gs2_runs[i].nwrite, new_run.gs2_runs[i].parameter_hash]
|
|
101
|
+
##########gs2_runs[i].restart(new_run.gs2_runs[i])
|
|
102
|
+
###########ep ['gs2_runs[i] after', gs2_runs[i].nwrite, new_run.gs2_runs[i].nwrite, new_run.gs2_runs[i].parameter_hash]
|
|
103
|
+
###########new_run.gs2_runs[i].run_name = new_run.run_name + (i+1).to_s
|
|
104
|
+
##########end
|
|
105
|
+
##########end
|
|
106
|
+
##@runner.submit(new_run)
|
|
107
|
+
#new_run
|
|
108
|
+
end
|
|
109
|
+
# This is a hook which gets called just before submitting a simulation. It sets up the folder and generates any necessary input files.
|
|
110
|
+
def generate_input_file
|
|
111
|
+
check_parameters
|
|
112
|
+
if @restart_id
|
|
113
|
+
@runner.run_list[@restart_id].restart(self)
|
|
114
|
+
end
|
|
115
|
+
@diagdir = "."
|
|
116
|
+
@n_procs_sim = actual_number_of_processors
|
|
117
|
+
write_input_file
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
def self.parse_input_file(input_file, strict=true)
|
|
121
|
+
if FileTest.file? input_file
|
|
122
|
+
text = File.read(input_file)
|
|
123
|
+
else
|
|
124
|
+
text = input_file
|
|
125
|
+
end
|
|
126
|
+
i = 0
|
|
127
|
+
text.gsub!(/^(&species)/i){p $~; "#{$1}_#{i+=1}"}
|
|
128
|
+
super(text)
|
|
129
|
+
end
|
|
130
|
+
def namelist_text(namelist, enum = nil)
|
|
131
|
+
hash = rcp.namelists[namelist]
|
|
132
|
+
text = ""
|
|
133
|
+
ext = enum ? "_#{enum}" : ""
|
|
134
|
+
text << "!#{'='*30}\n!#{hash[:description]} #{enum} \n!#{'='*30}\n" if hash[:description]
|
|
135
|
+
#text << "&#{namelist}#{ext}\n"
|
|
136
|
+
text << "&#{namelist}\n"
|
|
137
|
+
hash[:variables].each do |var, var_hash|
|
|
138
|
+
code_var = (var_hash[:code_name] or var)
|
|
139
|
+
cr_var = var+ext.to_sym
|
|
140
|
+
value = send(cr_var)
|
|
141
|
+
if send(cr_var) and (not var_hash[:should_include] or eval(var_hash[:should_include]))
|
|
142
|
+
if value.kind_of? Array
|
|
143
|
+
value.each_with_index do |v, i|
|
|
144
|
+
output = formatted_variable_output(v)
|
|
145
|
+
text << " #{code_var}(#{i+1}) = #{output} #{var_hash[:description] ? "! #{var_hash[:description]}": ""}\n"
|
|
146
|
+
end
|
|
147
|
+
else
|
|
148
|
+
output = formatted_variable_output(value)
|
|
149
|
+
text << " #{code_var} = #{output} #{var_hash[:description] ? "! #{var_hash[:description]}": ""}\n"
|
|
150
|
+
end
|
|
151
|
+
elsif rcp.namelists_to_print_not_specified? and rcp.namelists_to_print_not_specified.include?(namelist)
|
|
152
|
+
text << " ! #{code_var} not specified --- #{var_hash[:description]}\n"
|
|
153
|
+
end
|
|
154
|
+
end
|
|
155
|
+
text << "/\n\n"
|
|
156
|
+
text
|
|
157
|
+
end
|
|
158
|
+
|
|
159
|
+
def check_parameters
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
|
|
164
|
+
def vim_output
|
|
165
|
+
system "vim -Ro #{output_file} #{error_file}"
|
|
166
|
+
end
|
|
167
|
+
alias :vo :vim_output
|
|
168
|
+
|
|
169
|
+
# This command uses the infrastructure provided by Run::FortranNamelist, provided by CodeRunner itself.
|
|
170
|
+
def write_input_file
|
|
171
|
+
#File.open("#@run_name.in", 'w'){|file| file.puts input_file_text}
|
|
172
|
+
File.open("parameters", 'w'){|file| file.puts input_file_text}
|
|
173
|
+
end
|
|
174
|
+
|
|
175
|
+
# Parameters which follow the Trinity executable, in this case just the input file.
|
|
176
|
+
def parameter_string
|
|
177
|
+
""
|
|
178
|
+
end
|
|
179
|
+
|
|
180
|
+
def parameter_transition
|
|
181
|
+
end
|
|
182
|
+
|
|
183
|
+
def generate_component_runs
|
|
184
|
+
#puts "HERE"
|
|
185
|
+
end
|
|
186
|
+
|
|
187
|
+
|
|
188
|
+
|
|
189
|
+
@source_code_subfolders = []
|
|
190
|
+
|
|
191
|
+
# This method, as its name suggests, is called whenever CodeRunner is asked to analyse a run directory. This happens if the run status is not :Complete, or if the user has specified recalc_all(-A on the command line) or reprocess_all (-a on the command line).
|
|
192
|
+
#
|
|
193
|
+
def process_directory_code_specific
|
|
194
|
+
get_status
|
|
195
|
+
#p ['id is', id, 'ctd is ', ctd]
|
|
196
|
+
#if ctd
|
|
197
|
+
#get_global_results
|
|
198
|
+
#end
|
|
199
|
+
#p ['fusionQ is ', fusionQ]
|
|
200
|
+
#@percent_complete = completed_timesteps.to_f / ntstep.to_f * 100.0
|
|
201
|
+
end
|
|
202
|
+
|
|
203
|
+
def get_status
|
|
204
|
+
return :Unknown
|
|
205
|
+
end
|
|
206
|
+
|
|
207
|
+
|
|
208
|
+
@fortran_namelist_source_file_match = /((\.F9[05])|(\.fpp)|COMDAT.inc)$/
|
|
209
|
+
@fortran_namelist_source_file_match = /((\.F9[05]))$/
|
|
210
|
+
|
|
211
|
+
def input_file_header
|
|
212
|
+
<<EOF
|
|
213
|
+
!==============================================================================
|
|
214
|
+
! GENE input file automatically generated by CodeRunner
|
|
215
|
+
!==============================================================================
|
|
216
|
+
!
|
|
217
|
+
! GENE is a code for solving the nonlinear gyrokinetic equation.
|
|
218
|
+
!
|
|
219
|
+
! See http://www2.ipp.mpg.de/~fsj/gene/
|
|
220
|
+
!
|
|
221
|
+
! CodeRunner is a framework for the automated running and analysis
|
|
222
|
+
! of large simulations.
|
|
223
|
+
!
|
|
224
|
+
! See http://coderunner.sourceforge.net
|
|
225
|
+
!
|
|
226
|
+
! Created #{Time.now.to_s}
|
|
227
|
+
! by CodeRunner version #{CodeRunner::CODE_RUNNER_VERSION.to_s}
|
|
228
|
+
!
|
|
229
|
+
!==============================================================================
|
|
230
|
+
|
|
231
|
+
EOF
|
|
232
|
+
end
|
|
233
|
+
def self.defaults_file_header
|
|
234
|
+
<<EOF1
|
|
235
|
+
############################################################################
|
|
236
|
+
# #
|
|
237
|
+
# Automatically generated defaults file for the GENE CodeRunner module #
|
|
238
|
+
# #
|
|
239
|
+
# This defaults file specifies a set of defaults for GENE which are #
|
|
240
|
+
# used by CodeRunner to set up and run GENE simulations. #
|
|
241
|
+
# #
|
|
242
|
+
############################################################################
|
|
243
|
+
|
|
244
|
+
# Created: #{Time.now.to_s}
|
|
245
|
+
|
|
246
|
+
@defaults_file_description = ""
|
|
247
|
+
EOF1
|
|
248
|
+
end
|
|
249
|
+
|
|
250
|
+
|
|
251
|
+
def input_file_extension
|
|
252
|
+
''
|
|
253
|
+
end
|
|
254
|
+
|
|
255
|
+
@msdatching_regex = Regexp.new('(^|\A)(?<everything>[^!
|
|
256
|
+
]*?\b #a word boundary
|
|
257
|
+
|
|
258
|
+
(?<name>[A-Za-z_]\w*) # the name, which must be a single word (not beginning
|
|
259
|
+
# with a digit) followed by
|
|
260
|
+
|
|
261
|
+
\s*=\s* # an equals sign (possibly with whitespace either side), then
|
|
262
|
+
|
|
263
|
+
(?<default>(?> # the default answer, which can be either:
|
|
264
|
+
|
|
265
|
+
(?<string>' + Regexp.quoted_string.to_s + ') # a quoted string
|
|
266
|
+
|
|
267
|
+
| # or
|
|
268
|
+
|
|
269
|
+
|
|
270
|
+
(?<float>\-?(?:(?>\d+\.\d*)|(?>\d*\.\d+))(?:[eEdD][+-]?\d+)?)(?:_RKIND)? # a floating point number
|
|
271
|
+
|
|
272
|
+
| #or
|
|
273
|
+
|
|
274
|
+
(?<int>\-?\d++) # an integer
|
|
275
|
+
|
|
276
|
+
| #or
|
|
277
|
+
|
|
278
|
+
(?<complex>\((?:\-?(?:(?>\d+\.\d*)|(?>\d*\.\d+))(?:[eEdD][+-]?\d+)?),\s*(?:\-?(?:(?>\d+\.\d*)|(?>\d*\.\d+))(?:[eEdD][+-]?\d+)?)\)) #a complex number
|
|
279
|
+
|
|
280
|
+
| #or
|
|
281
|
+
|
|
282
|
+
|
|
283
|
+
(?:(?<word>\S+)(?=\s|\)|\]|[\n\r]+|\Z)) # a single word containing no spaces
|
|
284
|
+
# which must be followed by a space or ) or ] or \n or \Z
|
|
285
|
+
|
|
286
|
+
)))', Regexp::EXTENDED)
|
|
287
|
+
end
|
|
288
|
+
end
|
|
289
|
+
|