2 # SPDX-License-Identifier: GPL-2.0+
3 # vim: ts=2:sw=2:et:tw=80:nowrap
5 # This is simply to aide in creating the entries in the order of the value of
6 # the device-global NI signal/terminal constants defined in comedi.h
9 from csv_collection import CSVCollection
12 def c_to_o(filename, prefix='\t\t\t\t\t ni_routing/', suffix=' \\'):
13 if not filename.endswith('.c'):
15 return prefix + filename.rpartition('.c')[0] + '.o' + suffix
18 def routedict_to_structinit_single(name, D, return_name=False):
21 '\t.family = "{}",'.format(name),
22 '\t.register_values = {',
24 '\t\t * destination = {',
25 '\t\t * source = register value,',
31 # print table with index0:src, index1:dest
32 D0 = D # (src-> dest->reg_value)
36 for src, destD in D.items():
37 for dest, val in destD.items():
38 D0.setdefault(dest, {})[src] = val
41 D0 = sorted(D0.items(), key=lambda i: eval(i[0], comedi_h.__dict__, Locals))
43 for D0_sig, D1_D in D0:
44 D1 = sorted(D1_D.items(), key=lambda i: eval(i[0], comedi_h.__dict__, Locals))
46 lines.append('\t\t[B({})] = {{'.format(D0_sig))
47 for D1_sig, value in D1:
48 if not re.match('[VIU]\([^)]*\)', value):
49 sys.stderr.write('Invalid register format: {}\n'.format(repr(value)))
51 'Register values should be formatted with V(),I(),or U()\n')
52 raise RuntimeError('Invalid register values format')
53 lines.append('\t\t\t[B({})]\t= {},'.format(D1_sig, value))
54 lines.append('\t\t},')
57 lines = '\n'.join(lines)
64 def routedict_to_routelist_single(name, D, indent=1):
76 # data is src -> dest-list
81 # data is dest -> src-list
85 for src, destD in D.items():
86 for dest, val in destD.items():
87 D0.setdefault(dest, {})[src] = val
89 # Sort by order of device-global names (numerically)
90 D0 = sorted(D0.items(), key=lambda i: eval(i[0], comedi_h.__dict__, Locals))
92 lines = [ '{I0}.device = "{name}",\n'
93 '{I0}.routes = (struct ni_route_set[]){{'
94 .format(name=name, **indents) ]
95 for D0_sig, D1_D in D0:
96 D1 = [ k for k,v in D1_D.items() if v ]
97 D1.sort(key=lambda i: eval(i, comedi_h.__dict__, Locals))
99 lines.append('{I1}{{\n{I2}.{keyname} = {D0_sig},\n'
100 '{I2}.{valname} = (int[]){{'
101 .format(keyname=keyname, valname=valname, D0_sig=D0_sig, **indents)
104 lines.append( '{I3}{D1_sig},'.format(D1_sig=D1_sig, **indents) )
105 lines.append( '{I3}0, /* Termination */'.format(**indents) )
107 lines.append('{I2}}}\n{I1}}},'.format(**indents))
109 lines.append('{I1}{{ /* Termination of list */\n{I2}.{keyname} = 0,\n{I1}}},'
110 .format(keyname=keyname, **indents))
112 lines.append('{I0}}},'.format(**indents))
114 return '\n'.join(lines)
117 class DeviceRoutes(CSVCollection):
118 MKFILE_SEGMENTS = 'device-route.mk'
119 SET_C = 'ni_device_routes.c'
120 ITEMS_DIR = 'ni_device_routes'
124 output_file_top = """\
125 // SPDX-License-Identifier: GPL-2.0+
126 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
128 * comedi/drivers/ni_routing/{filename}
129 * List of valid routes for specific NI boards.
131 * COMEDI - Linux Control and Measurement Device Interface
132 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
134 * This program is free software; you can redistribute it and/or modify
135 * it under the terms of the GNU General Public License as published by
136 * the Free Software Foundation; either version 2 of the License, or
137 * (at your option) any later version.
139 * This program is distributed in the hope that it will be useful,
140 * but WITHOUT ANY WARRANTY; without even the implied warranty of
141 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
142 * GNU General Public License for more details.
146 * The contents of this file are generated using the tools in
147 * comedi/drivers/ni_routing/tools
149 * Please use those tools to help maintain the contents of this file.
152 #include "ni_device_routes.h"
153 #include "{extern_h}"\
154 """.format(filename=SET_C, extern_h=os.path.join(ITEMS_DIR, EXTERN_H))
157 /* SPDX-License-Identifier: GPL-2.0+ */
158 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
160 * comedi/drivers/ni_routing/{filename}
161 * List of valid routes for specific NI boards.
163 * COMEDI - Linux Control and Measurement Device Interface
164 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
166 * This program is free software; you can redistribute it and/or modify
167 * it under the terms of the GNU General Public License as published by
168 * the Free Software Foundation; either version 2 of the License, or
169 * (at your option) any later version.
171 * This program is distributed in the hope that it will be useful,
172 * but WITHOUT ANY WARRANTY; without even the implied warranty of
173 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
174 * GNU General Public License for more details.
178 * The contents of this file are generated using the tools in
179 * comedi/drivers/ni_routing/tools
181 * Please use those tools to help maintain the contents of this file.
184 #ifndef _COMEDI_DRIVERS_NI_ROUTING_NI_DEVICE_ROUTES_EXTERN_H
185 #define _COMEDI_DRIVERS_NI_ROUTING_NI_DEVICE_ROUTES_EXTERN_H
187 #include "../ni_device_routes.h"
191 #endif //_COMEDI_DRIVERS_NI_ROUTING_NI_DEVICE_ROUTES_EXTERN_H
194 single_output_file_top = """\
195 // SPDX-License-Identifier: GPL-2.0+
196 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
198 * comedi/drivers/ni_routing/{filename}
199 * List of valid routes for specific NI boards.
201 * COMEDI - Linux Control and Measurement Device Interface
202 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
204 * This program is free software; you can redistribute it and/or modify
205 * it under the terms of the GNU General Public License as published by
206 * the Free Software Foundation; either version 2 of the License, or
207 * (at your option) any later version.
209 * This program is distributed in the hope that it will be useful,
210 * but WITHOUT ANY WARRANTY; without even the implied warranty of
211 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
212 * GNU General Public License for more details.
216 * The contents of this file are generated using the tools in
217 * comedi/drivers/ni_routing/tools
219 * Please use those tools to help maintain the contents of this file.
222 #include "../ni_device_routes.h"
223 #include "{extern_h}"
225 struct ni_device_routes {table_name} = {{\
228 def __init__(self, pattern='csv/device_routes/*.csv'):
229 super(DeviceRoutes,self).__init__(pattern)
231 def to_listinit(self):
232 chunks = [ self.output_file_top,
234 'struct ni_device_routes *const ni_device_routes_list[] = {'
236 # put the sheets in lexical order of device numbers then bus
237 sheets = sorted(self.items(), key=lambda i : tuple(i[0].split('-')[::-1]) )
240 objs = [c_to_o(self.SET_C)]
242 for sheet,D in sheets:
244 dev_table_name = 'ni_{}_device_routes'.format(S.replace('-','_'))
245 sheet_filename = os.path.join(self.ITEMS_DIR,'{}.c'.format(S))
246 externs.append('extern struct ni_device_routes {};'.format(dev_table_name))
248 chunks.append('\t&{},'.format(dev_table_name))
251 self.single_output_file_top.format(
252 filename = sheet_filename,
253 table_name = dev_table_name,
254 extern_h = self.EXTERN_H,
256 routedict_to_routelist_single(S, D),
260 objs.append(c_to_o(sheet_filename))
262 with open(os.path.join(self.OUTPUT_DIR, sheet_filename), 'w') as f:
263 f.write('\n'.join(s_chunks))
266 with open(os.path.join(self.OUTPUT_DIR, self.MKFILE_SEGMENTS), 'w') as f:
267 f.write('# This is the segment that should be included in comedi/drivers/Makefile\n')
268 f.write('ni_routing-objs\t\t\t\t+= \\\n')
269 f.write('\n'.join(objs))
272 EXTERN_H = os.path.join(self.ITEMS_DIR, self.EXTERN_H)
273 with open(os.path.join(self.OUTPUT_DIR, EXTERN_H), 'w') as f:
274 f.write(self.extern_header.format(
275 filename=EXTERN_H, externs='\n'.join(externs)))
277 chunks.append('\tNULL,') # terminate list
279 return '\n'.join(chunks)
282 filename=os.path.join(self.OUTPUT_DIR, self.SET_C)
285 os.makedirs(os.path.join(self.OUTPUT_DIR, self.ITEMS_DIR))
288 with open(filename,'w') as f:
289 f.write( self.to_listinit() )
293 class RouteValues(CSVCollection):
294 MKFILE_SEGMENTS = 'route-values.mk'
295 SET_C = 'ni_route_values.c'
296 ITEMS_DIR = 'ni_route_values'
300 output_file_top = """\
301 // SPDX-License-Identifier: GPL-2.0+
302 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
304 * comedi/drivers/ni_routing/{filename}
305 * Route information for NI boards.
307 * COMEDI - Linux Control and Measurement Device Interface
308 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
310 * This program is free software; you can redistribute it and/or modify
311 * it under the terms of the GNU General Public License as published by
312 * the Free Software Foundation; either version 2 of the License, or
313 * (at your option) any later version.
315 * This program is distributed in the hope that it will be useful,
316 * but WITHOUT ANY WARRANTY; without even the implied warranty of
317 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
318 * GNU General Public License for more details.
322 * This file includes the tables that are a list of all the values of various
323 * signals routes available on NI hardware. In many cases, one does not
324 * explicitly make these routes, rather one might indicate that something is
325 * used as the source of one particular trigger or another (using
328 * The contents of this file are generated using the tools in
329 * comedi/drivers/ni_routing/tools
331 * Please use those tools to help maintain the contents of this file.
334 #include "ni_route_values.h"
335 #include "{extern_h}"\
336 """.format(filename=SET_C, extern_h=os.path.join(ITEMS_DIR, EXTERN_H))
339 /* SPDX-License-Identifier: GPL-2.0+ */
340 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
342 * comedi/drivers/ni_routing/{filename}
343 * List of valid routes for specific NI boards.
345 * COMEDI - Linux Control and Measurement Device Interface
346 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
348 * This program is free software; you can redistribute it and/or modify
349 * it under the terms of the GNU General Public License as published by
350 * the Free Software Foundation; either version 2 of the License, or
351 * (at your option) any later version.
353 * This program is distributed in the hope that it will be useful,
354 * but WITHOUT ANY WARRANTY; without even the implied warranty of
355 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
356 * GNU General Public License for more details.
360 * The contents of this file are generated using the tools in
361 * comedi/drivers/ni_routing/tools
363 * Please use those tools to help maintain the contents of this file.
366 #ifndef _COMEDI_DRIVERS_NI_ROUTING_NI_ROUTE_VALUES_EXTERN_H
367 #define _COMEDI_DRIVERS_NI_ROUTING_NI_ROUTE_VALUES_EXTERN_H
369 #include "../ni_route_values.h"
373 #endif //_COMEDI_DRIVERS_NI_ROUTING_NI_ROUTE_VALUES_EXTERN_H
376 single_output_file_top = """\
377 // SPDX-License-Identifier: GPL-2.0+
378 /* vim: set ts=8 sw=8 noet tw=80 nowrap: */
380 * comedi/drivers/ni_routing/{filename}
381 * Route information for {sheet} boards.
383 * COMEDI - Linux Control and Measurement Device Interface
384 * Copyright (C) 2016 Spencer E. Olson <olsonse@umich.edu>
386 * This program is free software; you can redistribute it and/or modify
387 * it under the terms of the GNU General Public License as published by
388 * the Free Software Foundation; either version 2 of the License, or
389 * (at your option) any later version.
391 * This program is distributed in the hope that it will be useful,
392 * but WITHOUT ANY WARRANTY; without even the implied warranty of
393 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
394 * GNU General Public License for more details.
398 * This file includes a list of all the values of various signals routes
399 * available on NI 660x hardware. In many cases, one does not explicitly make
400 * these routes, rather one might indicate that something is used as the source
401 * of one particular trigger or another (using *_src=TRIG_EXT).
403 * The contents of this file can be generated using the tools in
404 * comedi/drivers/ni_routing/tools. This file also contains specific notes to
405 * this family of devices.
407 * Please use those tools to help maintain the contents of this file, but be
408 * mindful to not lose the notes already made in this file, since these notes
409 * are critical to a complete undertsanding of the register values of this
413 #include "../ni_route_values.h"
414 #include "{extern_h}"
416 const struct family_route_values {table_name} = {{\
419 def __init__(self, pattern='csv/route_values/*.csv'):
420 super(RouteValues,self).__init__(pattern)
422 def to_structinit(self):
423 chunks = [ self.output_file_top,
425 'const struct family_route_values *const ni_all_route_values[] = {'
427 # put the sheets in lexical order for consistency
428 sheets = sorted(self.items(), key=lambda i : i[0] )
431 objs = [c_to_o(self.SET_C)]
433 for sheet,D in sheets:
435 fam_table_name = '{}_route_values'.format(S.replace('-','_'))
436 sheet_filename = os.path.join(self.ITEMS_DIR,'{}.c'.format(S))
437 externs.append('extern const struct family_route_values {};'.format(fam_table_name))
439 chunks.append('\t&{},'.format(fam_table_name))
442 self.single_output_file_top.format(
443 filename = sheet_filename,
444 sheet = sheet.upper(),
445 table_name = fam_table_name,
446 extern_h = self.EXTERN_H,
448 routedict_to_structinit_single(S, D),
452 objs.append(c_to_o(sheet_filename))
454 with open(os.path.join(self.OUTPUT_DIR, sheet_filename), 'w') as f:
455 f.write('\n'.join(s_chunks))
458 with open(os.path.join(self.OUTPUT_DIR, self.MKFILE_SEGMENTS), 'w') as f:
459 f.write('# This is the segment that should be included in comedi/drivers/Makefile\n')
460 f.write('ni_routing-objs\t\t\t\t+= \\\n')
461 f.write('\n'.join(objs))
464 EXTERN_H = os.path.join(self.ITEMS_DIR, self.EXTERN_H)
465 with open(os.path.join(self.OUTPUT_DIR, EXTERN_H), 'w') as f:
466 f.write(self.extern_header.format(
467 filename=EXTERN_H, externs='\n'.join(externs)))
469 chunks.append('\tNULL,') # terminate list
471 return '\n'.join(chunks)
474 filename=os.path.join(self.OUTPUT_DIR, self.SET_C)
477 os.makedirs(os.path.join(self.OUTPUT_DIR, self.ITEMS_DIR))
480 with open(filename,'w') as f:
481 f.write( self.to_structinit() )
486 if __name__ == '__main__':
488 parser = argparse.ArgumentParser()
489 parser.add_argument( '--route_values', action='store_true',
490 help='Extract route values from csv/route_values/*.csv' )
491 parser.add_argument( '--device_routes', action='store_true',
492 help='Extract route values from csv/device_routes/*.csv' )
493 args = parser.parse_args()
495 if args.route_values:
496 KL.append( RouteValues )
497 if args.device_routes:
498 KL.append( DeviceRoutes )
500 parser.error('nothing to do...')