x393_export_c.py 169 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
from __future__ import division
from __future__ import print_function

'''
# Copyright (C) 2015, Elphel.inc.
# Class to export hardware definitions from Verilog parameters  
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http:#www.gnu.org/licenses/>.

@author:     Andrey Filippov
@copyright:  2015 Elphel, Inc.
@license:    GPLv3.0+
@contact:    andrey@elphel.coml
@deffield    updated: Updated
'''
__author__ = "Andrey Filippov"
__copyright__ = "Copyright 2015, Elphel, Inc."
__license__ = "GPL"
__version__ = "3.0+"
__maintainer__ = "Andrey Filippov"
__email__ = "andrey@elphel.com"
__status__ = "Development"
#import sys
#import pickle
35 36 37
import os
import errno
import datetime
38 39
import vrlg
class X393ExportC(object):
40 41 42 43 44 45 46 47
    DRY_MODE =    True # True
    DEBUG_MODE =  1
    MAXI0_BASE =  0x40000000
    MAXI0_RANGE = 0x00003000
    verbose =     1
    func_decl =   None
    func_def =    None
    typedefs =    None
48 49 50 51 52 53 54
    gen_dir =       "generated"
    typdefs_file =  "x393_types.h" # typdef for hardware registers
    header_file =   "x393.h"       # constant definitions and function declarations
    func_def_file = "x393.c"       # functions definitions
    defs_file =     "x393_defs.h"  # alternative - constants and address definitions
    map_file =      "x393_map.h"   # address map as  defines
    
55 56 57 58 59 60 61 62 63
    dflt_frmt_spcs={'ftype':        'u32',
                    'showBits':     True,
                    'showDefaults': True,
                    'showReserved': False,
                    'nameLength':   15,
                    'lastPad':      False,
                    'macroNameLen': 48,
                    'showType':     True,
                    'showRange':    True,
64
                    'nameMembers':  False, # True, #name each struct in a union
65
                    'data32':       'd32', #union branch that is always u32 ("" to disable)
66 67 68 69 70 71 72 73 74 75
#                    'declare':(26,48,0, 80),  #function name, arguments, (body), comments
#                    'define': (26,48,72,106), #function name, arguments, body, comments
#                    'declare':(29,59,0, 91),  #function name, arguments, (body), comments
#                    'define': (29,59,83,117), #function name, arguments, body, comments
#                    'declare':(29,59,0, 103),  #function name, arguments, (body), comments
#                    'define': (29,59,83,127), #function name, arguments, body, comments
                    'declare':(29,65,0, 113),  #function name, arguments, (body), comments
                    'define': (29,65,85,130), #function name, arguments, body, comments
                    
                    } 
76 77 78 79 80 81 82 83

    def __init__(self, debug_mode=1,dry_mode=True, saveFileName=None):
        self.DEBUG_MODE=  debug_mode
        self.DRY_MODE=    dry_mode
        try:
            self.verbose=vrlg.VERBOSE
        except:
            pass
84
        
85
    def export_all(self):
86 87 88 89 90 91 92 93 94
        self.func_decl=[]
        self.func_def= []
        self.save_typedefs(self.gen_dir, self.typdefs_file)
        
        
        self.save_header_file      (self.gen_dir, self.header_file)
        self.save_func_def_file    (self.gen_dir, self.func_def_file)
        self.save_defines_file     (self.gen_dir, self.defs_file)
        self.save_harware_map_file (self.gen_dir, self.map_file)
95 96
        return "OK"
    
97 98 99 100 101 102 103 104 105
    def make_generated(self, path):
        try:
            os.makedirs(path)
        except OSError as exception:
            if exception.errno != errno.EEXIST:
                raise
            
    def generated_fileHeader(self, filename, description):
        header_template="""/*******************************************************************************
106 107 108 109
 * @file %s
 * @date %s  
 * @author auto-generated file, see %s
 * @brief %s
110
 *******************************************************************************/"""
111 112 113 114
        script_name = os.path.basename(__file__)
        if script_name[-1] == "c":
            script_name = script_name[:-1] 
        return header_template%(filename, datetime.date.today().isoformat(), script_name, description)
115 116 117 118 119 120 121 122 123 124 125 126 127 128
        
    def save_typedefs(self, directory, filename):
        description = 'typedef definitions for the x393 hardware registers'
        header = self.generated_fileHeader(filename,description)
        txt=self.get_typedefs(frmt_spcs = None)
        self.make_generated(os.path.abspath(os.path.join(os.path.dirname(__file__), directory)))
        with open(os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename)),"w") as out_file:
            print(header,file=out_file)
            print(txt,file=out_file)
        print ("%s are written to  to %s"%(description, os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename))))
        
    def save_header_file(self, directory, filename):
        description = 'Constants definitions and functions declarations to access x393 hardware registers'
        header = self.generated_fileHeader(filename,description)
129 130
        ld= self.define_macros()
        ld+=self.define_other_macros()
131
        # Includes section
132
        txt = '\n#include "x393_types.h"\n'
133
        txt +='//#include "elphel/x393_defs.h // alternative variant"\n\n'
134
        txt +='// See elphel/x393_map.h for the ordered list of all I/O register addresses used\n'
135 136 137
        txt +=  '// init_mmio_ptr() should be called once before using any of the other declared functions\n\n'
        txt +=  'int init_mmio_ptr(void);\n'
        
138
        for d in ld:
139 140 141 142 143 144 145 146 147 148 149 150 151 152
            fd=self.expand_define_maxi0(d, mode = "func_decl",frmt_spcs = None)
            if fd:
                txt += fd + "\n"
        self.make_generated(os.path.abspath(os.path.join(os.path.dirname(__file__), directory)))
        with open(os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename)),"w") as out_file:
            print(header,file=out_file)
            print(txt,file=out_file)
        print ("%s are written to  to %s"%(description, os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename))))
        
    def save_func_def_file(self, directory, filename):
        description = 'Functions definitions to access x393 hardware registers'
        header = self.generated_fileHeader(filename,description)
        ld= self.define_macros()
        ld+=self.define_other_macros()
153 154 155
        # Includes section
        txt = '\n#include <linux/io.h>\n'
        txt +=  '#include "x393.h"\n\n'
Andrey Filippov's avatar
Andrey Filippov committed
156
        txt +=  'static void __iomem* mmio_ptr;\n\n'
157 158
        txt +=  '// init_mmio_ptr() should be called once before using any of the other defined functions\n\n'
        txt +=  'int init_mmio_ptr(void) {mmio_ptr = ioremap(0x%08x, 0x%08x); if (!mmio_ptr) return -1; else return 0;}\n'%(self.MAXI0_BASE,self.MAXI0_RANGE)
159

160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190
        for d in ld:
            fd=self.expand_define_maxi0(d, mode = "func_def",frmt_spcs = None)
            if fd:
                txt += fd + "\n"
        self.make_generated(os.path.abspath(os.path.join(os.path.dirname(__file__), directory)))
        with open(os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename)),"w") as out_file:
            print(header,file=out_file)
            print(txt,file=out_file)
        print ("%s are written to  to %s"%(description, os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename))))

    def save_defines_file(self, directory, filename):
        description = 'Constants and hardware addresses definitions to access x393 hardware registers'
        header = self.generated_fileHeader(filename,description)
        ld= self.define_macros()
        ld+=self.define_other_macros()
        txt = ""
        for d in ld:
            fd=self.expand_define_maxi0(d, mode = "defines",frmt_spcs = None)
            if fd:
                txt += fd + "\n"
        self.make_generated(os.path.abspath(os.path.join(os.path.dirname(__file__), directory)))
        with open(os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename)),"w") as out_file:
            print(header,file=out_file)
            print(txt,file=out_file)
        print ("%s are written to  to %s"%(description, os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename))))
 
    def save_harware_map_file(self, directory, filename):
        description = 'Sorted hardware addresses map'
        header = self.generated_fileHeader(filename,description)
        ld= self.define_macros()
        ld+=self.define_other_macros()
191
        sam = self.expand_define_parameters(ld)
192
        txt = ""
193
        for d in sam:
194 195 196 197 198 199 200 201 202 203 204
#            print(self.expand_define_maxi0(d, mode = "defines", frmt_spcs = None))
            fd=self.expand_define_maxi0(d, mode = "defines",frmt_spcs = None)
            if fd:
                txt += fd + "\n"
        self.make_generated(os.path.abspath(os.path.join(os.path.dirname(__file__), directory)))
        with open(os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename)),"w") as out_file:
            print(header,file=out_file)
            print(txt,file=out_file)
        print ("%s is written to  to %s"%(description, os.path.abspath(os.path.join(os.path.dirname(__file__), directory, filename))))
 
    def get_typedefs(self, frmt_spcs = None):
205
#        print("Will list bitfields typedef and comments")
206 207
        self.typedefs={}
        self.typedefs['u32']= {'comment':'unsigned 32-bit', 'code':'', 'size':32, 'type':''}
208 209 210 211
        stypedefs = ""
        
        stypedefs += self.get_typedef32(comment =   "Status generation control ",
                                 data =      self._enc_status_control(),
212
                                 name =      "x393_status_ctrl",  typ="rw",
213 214 215
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel operation mode",
                                 data =      self._enc_func_encode_mode_scan_tiled(),
216
                                 name =      "x393_mcntrl_mode_scan",  typ="wo",
217 218 219
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel window tile size/step (tiled only)",
                                 data =      self._enc_window_tile_whs(),
220
                                 name =      "x393_mcntrl_window_tile_whs",  typ="wo",
221 222 223
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel window size",
                                 data =      self._enc_window_wh(),
224
                                 name =      "x393_mcntrl_window_width_height",  typ="wo",
225 226 227
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel window position",
                                 data =      self._enc_window_lt(),
228
                                 name =      "x393_mcntrl_window_left_top",  typ="wo",
229 230 231
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel scan start (debug feature)",
                                 data =      self._enc_window_sxy(),
232
                                 name =      "x393_mcntrl_window_startx_starty",  typ="wo",
233 234 235
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel window full (padded) width",
                                 data =      self._enc_window_fw(),
236
                                 name =      "x393_mcntrl_window_full_width",  typ="wo",
237 238 239
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel last frame number in a buffer (number of frames minus 1)",
                                 data =      self._enc_window_last_frame_number(),
240
                                 name =      "x393_mcntrl_window_last_frame_num",  typ="wo",
241 242 243
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel frame start address increment (for next frame in a buffer)",
                                 data =      self._enc_window_frame_sa_inc(),
244
                                 name =      "x393_mcntrl_window_frame_sa_inc",  typ="wo",
245 246 247
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory channel frame start address for the first frame in a buffer",
                                 data =      self._enc_window_frame_sa(),
248
                                 name =      "x393_mcntrl_window_frame_sa",  typ="wo",
249 250 251
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "PS PIO (software-programmed DDR3) access sequences enable and reset",
                                 data =      self._enc_ps_pio_en_rst(),
252
                                 name =      "x393_ps_pio_en_rst",  typ="wo",
253 254 255
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "PS PIO (software-programmed DDR3) access sequences control",
                                 data =      self._enc_ps_pio_cmd(),
256
                                 name =      "x393_ps_pio_cmd",  typ="wo",
257 258 259 260
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "x393 generic status register",
                                 data =      self._enc_status(),
261
                                 name =      "x393_status",  typ="ro",
262 263 264
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory PHY status",
                                 data =      self._enc_status_mcntrl_phy(),
265
                                 name =      "x393_status_mcntrl_phy",  typ="ro",
266 267 268
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory controller requests status",
                                 data =      self._enc_status_mcntrl_top(),
269
                                 name =      "x393_status_mcntrl_top",  typ="ro",
270 271 272
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory software access status",
                                 data =      self._enc_status_mcntrl_ps(),
273
                                 name =      "x393_status_mcntrl_ps",  typ="ro",
274 275 276
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory test channels access status",
                                 data =      self._enc_status_lintile(),
277
                                 name =      "x393_status_mcntrl_lintile",  typ="ro",
278 279 280
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Memory test channels status",
                                 data =      self._enc_status_testchn(),
281
                                 name =      "x393_status_mcntrl_testchn",  typ="ro",
282 283 284
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Membridge channel status",
                                 data =      self._enc_status_membridge(),
285
                                 name =      "x393_status_membridge",  typ="ro",
286 287 288 289
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "Sensor/multiplexer I/O pins status",
                                 data =      self._enc_status_sens_io(),
290
                                 name =      "x393_status_sens_io",  typ="ro",
291 292 293 294
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Sensor/multiplexer i2c status",
                                 data =      self._enc_status_sens_i2c(),
295
                                 name =      "x393_status_sens_i2c",  typ="ro",
296 297 298 299
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Command bits for test01 module (test frame memory accesses)",
                                 data =      self._enc_test01_mode(),
300
                                 name =      "x393_test01_mode",  typ="wo",
301 302 303 304
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Command for membridge",
                                 data =      self._enc_membridge_cmd(),
305
                                 name =      "x393_membridge_cmd",  typ="wo",
306 307 308
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Cache mode for membridge",
                                 data =      self._enc_membridge_mode(),
309
                                 name =      "x393_membridge_mode",  typ="wo",
310 311 312
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Address in 64-bit words",
                                 data =      self._enc_u29(),
313
                                 name =      "u29",  typ="wo",
314 315 316 317 318 319 320
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "I2C contol/table data",
                                 data =      [self._enc_i2c_tbl_addr(), # generate typedef union
                                              self._enc_i2c_tbl_wmode(),
                                              self._enc_i2c_tbl_rmode(),
                                              self._enc_i2c_ctrl()],
321
                                 name =      "x393_i2c_ctltbl",  typ="wo",
322 323 324 325
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "Write sensor channel mode register",
                                 data =      self._enc_sens_mode(),
326
                                 name =      "x393_sens_mode",  typ="wo",
327 328 329 330
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Write number of sensor frames to combine into one virtual (linescan mode)",
                                 data =      self._enc_sens_sync_mult(),
331
                                 name =      "x393_sens_sync_mult",  typ="wo",
332 333 334 335
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Write sensor number of lines to delay frame sync",
                                 data =      self._enc_sens_sync_late(),
336
                                 name =      "x393_sens_sync_late",  typ="wo",
337 338 339 340
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Configure memory controller priorities",
                                 data =      self._enc_mcntrl_priorities(),
341
                                 name =      "x393_arbite_pri",  typ="rw",
342 343 344 345
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Enable/disable memory controller channels",
                                 data =      self._enc_mcntrl_chnen(),
346
                                 name =      "x393_mcntr_chn_en",  typ="rw",
347 348 349 350
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "DQS and DQM patterns (DQM - 0, DQS 0xaa or 0x55)",
                                 data =      self._enc_mcntrl_dqs_dqm_patterns(),
351
                                 name =      "x393_mcntr_dqs_dqm_patt",  typ="rw",
352 353 354
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "DQ and DQS tristate control when turning on and off",
                                 data =      self._enc_mcntrl_dqs_dq_tri(),
355
                                 name =      "x393_mcntr_dqs_dqm_tri",  typ="rw",
356
                                 frmt_spcs = frmt_spcs)
357 358 359
        
        stypedefs += self.get_typedef32(comment =   "DDR3 memory controller I/O delay",
                                 data =      self._enc_mcntrl_dly(),
360
                                 name =      "x393_dly",  typ="rw",
361 362 363
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Extra delay in mclk (fDDR/2) cycles) to data write buffer",
                                 data =      self._enc_wbuf_dly(),
364
                                 name =      "x393_wbuf_dly",  typ="rw",
365 366 367 368
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "Control for the gamma-conversion module",
                                 data =      self._enc_gamma_ctl(),
369
                                 name =      "x393_gamma_ctl",  typ="rw",
370 371 372 373
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Write gamma table address/data",
                                 data =      [self._enc_gamma_tbl_addr(), # generate typedef union
                                              self._enc_gamma_tbl_data()],
374
                                 name =      "x393_gamma_tbl",  typ="wo",
375 376 377
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Heights of the first two subchannels frames",
                                 data =      self._enc_gamma_height01(),
378
                                 name =      "x393_gamma_height01m1",  typ="rw",
379 380 381
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Height of the third subchannel frame",
                                 data =      self._enc_gamma_height2(),
382
                                 name =      "x393_gamma_height2m1",  typ="rw",
383 384 385 386 387
                                 frmt_spcs = frmt_spcs)
        
        stypedefs += self.get_typedef32(comment =   "Sensor port I/O control",
                                 data =      [self._enc_sensio_ctrl_par12(),
                                              self._enc_sensio_ctrl_hispi()],
388
                                 name =      "x393_sensio_ctl",  typ="wo",
389 390 391
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Programming interface for multiplexer FPGA",
                                 data =      self._enc_sensio_jtag(),
392
                                 name =      "x393_sensio_jtag",  typ="wo",
393
                                 frmt_spcs = frmt_spcs)
394
        """
395 396 397
        stypedefs += self.get_typedef32(comment =   "Sensor delays (uses 4 DWORDs)",
                                 data =      [self._enc_sensio_dly_par12(),
                                              self._enc_sensio_dly_hispi()],
398
                                 name =      "x393_sensio_dly",  typ="rw",
399
                                 frmt_spcs = frmt_spcs)
400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421
        """                                 
        stypedefs += self.get_typedef32(comment =   "Sensor i/o timing register 0 (different meanings for different sensor types)",
                                 data =      [self._enc_sensio_par12_tim0(),
                                              self._enc_sensio_hispi_tim0()],
                                 name =      "x393_sensio_tim0",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Sensor i/o timing register 1 (different meanings for different sensor types)",
                                 data =      [self._enc_sensio_par12_tim1(),
                                              self._enc_sensio_hispi_tim1()],
                                 name =      "x393_sensio_tim1",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Sensor i/o timing register 2 (different meanings for different sensor types)",
                                 data =      [self._enc_sensio_par12_tim2(),
                                              self._enc_sensio_hispi_tim2()],
                                 name =      "x393_sensio_tim2",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Sensor i/o timing register 3 (different meanings for different sensor types)",
                                 data =      [self._enc_sensio_par12_tim3(),
                                              self._enc_sensio_hispi_tim3()],
                                 name =      "x393_sensio_tim3",  typ="rw",
                                 frmt_spcs = frmt_spcs)

422 423
        stypedefs += self.get_typedef32(comment =   "Set sensor frame width (0 - use received)",
                                 data =      self._enc_sensio_width(),
424
                                 name =      "x393_sensio_width",  typ="rw",
425 426 427 428 429 430 431 432 433 434 435 436 437
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Lens vignetting parameter (write address first, then data that may overlap som address bits)",
                                 data =      [self._enc_lens_addr(),
                                              self._enc_lens_ax(),
                                              self._enc_lens_ay(),
                                              self._enc_lens_bx(),
                                              self._enc_lens_by(),
                                              self._enc_lens_c(),
                                              self._enc_lens_scale(),
                                              self._enc_lens_fatzero_in(),
                                              self._enc_lens_fatzero_out(),
                                              self._enc_lens_post_scale()],
438
                                 name =      "x393_lens_corr",  typ="wo",
439 440 441
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Height of the subchannel frame for vignetting correction",
                                 data =      self._enc_lens_height_m1(),
442
                                 name =      "x393_lens_height_m1",  typ="rw",
443 444 445 446
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "Histogram window left/top margins",
                                 data =      self._enc_histogram_lt(),
447
                                 name =      "x393_hist_left_top",  typ="rw",
448 449 450
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Histogram window width and height minus 1 (0 use full)",
                                 data =      self._enc_histogram_wh_m1(),
451
                                 name =      "x393_hist_width_height_m1",  typ="rw",
452 453 454
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Histograms DMA mode",
                                 data =      self._enc_hist_saxi_mode(),
455
                                 name =      "x393_hist_saxi_mode",  typ="rw",
456 457 458
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Histograms DMA addresses",
                                 data =      self._enc_hist_saxi_page_addr(),
459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483
                                 name =      "x393_hist_saxi_addr",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor mode control",
                                 data =      self._enc_cmprs_mode(),
                                 name =      "x393_cmprs_mode",  typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor coring mode (table number)",
                                 data =      self._enc_cmprs_coring_sel(),
                                 name =      "x393_cmprs_coring_mode",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor color saturation",
                                 data =      self._enc_cmprs_color_sat(),
                                 name =      "x393_cmprs_colorsat",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor frame format",
                                 data =      self._enc_cmprs_format(),
                                 name =      "x393_cmprs_frame_format",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor interrupts control",
                                 data =      self._enc_cmprs_interrupts(),
                                 name =      "x393_cmprs_interrupts",  typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor tables load control",
                                 data =      self._enc_cmprs_table_addr(),
                                 name =      "x393_cmprs_table_addr",  typ="wo",
484
                                 frmt_spcs = frmt_spcs)
485 486 487 488
        stypedefs += self.get_typedef32(comment =   "Compressor channel status",
                                 data =      self._enc_cmprs_status(),
                                 name =      "x393_cmprs_status",  typ="ro",
                                 frmt_spcs = frmt_spcs)
489

490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546
        stypedefs += self.get_typedef32(comment =   "Compressor DMA buffer address (in 32-byte blocks)",
                                 data =      self._enc_cmprs_afimux_sa(),
                                 name =      "x393_afimux_sa",  typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor DMA buffer length (in 32-byte blocks)",
                                 data =      self._enc_cmprs_afimux_len(),
                                 name =      "x393_afimux_len", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor DMA channels reset",
                                 data =      self._enc_cmprs_afimux_rst(),
                                 name =      "x393_afimux_rst", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor DMA enable (global and channels)",
                                 data =      self._enc_cmprs_afimux_en(),
                                 name =      "x393_afimux_en", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor DMA report mode",
                                 data =      self._enc_cmprs_afimux_report(),
                                 name =      "x393_afimux_report", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Compressor DMA status",
                                 data =      self._enc_cmprs_afimux_status(),
                                 name =      "x393_afimux_status", typ="ro",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "GPIO output control",
                                 data =      self._enc_cmprs_gpio_out(),
                                 name =      "x393_gpio_set_pins", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "GPIO pins status",
                                 data =      self._enc_cmprs_gpio_status(),
                                 name =      "x393_gpio_status", typ="ro",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "RTC seconds",
                                 data =      self._enc_rtc_sec(),
                                 name =      "x393_rtc_sec", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "RTC microseconds",
                                 data =      self._enc_rtc_usec(),
                                 name =      "x393_rtc_usec", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "RTC correction",
                                 data =      self._enc_rtc_corr(),
                                 name =      "x393_rtc_corr", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "RTC status",
                                 data =      self._enc_rtc_status(),
                                 name =      "x393_rtc_status", typ="ro",
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "CAMSYNC I/O configuration",
                                 data =      self._enc_camsync_lines(),
                                 name =      "x393_camsync_io", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "CAMSYNC mode",
                                 data =      self._enc_camsync_mode(),
                                 name =      "x393_camsync_mode", typ="wo",
                                 frmt_spcs = frmt_spcs)
547 548 549 550
        stypedefs += self.get_typedef32(comment =   "CMDFRAMESEQ mode",
                                 data =      self._enc_cmdframeseq_mode(),
                                 name =      "x393_cmdframeseq_mode", typ="wo",
                                 frmt_spcs = frmt_spcs)
551 552 553 554
        stypedefs += self.get_typedef32(comment =   "CMDFRAMESEQ mode",
                                 data =      self._enc_cmdseqmux_status(),
                                 name =      "x393_cmdseqmux_status", typ="ro",
                                 frmt_spcs = frmt_spcs)
555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571
        stypedefs += self.get_typedef32(comment =   "Event logger status",
                                 data =      self._enc_logger_status(),
                                 name =      "x393_logger_status", typ="ro",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Event logger register address",
                                 data =      self._enc_logger_reg_addr(),
                                 name =      "x393_logger_address", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "Event logger register data",
                                 data =      [self._enc_logger_conf(),
                                              self._enc_logger_data()],
                                 name =      "x393_logger_data", typ="wo",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "MULT_SAXI DMA addresses/lengths in 32-bit DWORDS",
                                 data =      self._enc_mult_saxi_addr(),
                                 name =      "x393_mult_saxi_al", typ="rw", # some - wo, others - ro
                                 frmt_spcs = frmt_spcs)
572 573 574 575 576 577 578 579 580 581 582 583 584 585 586

        stypedefs += self.get_typedef32(comment =   "MULTICLK reset/power down controls",
                                 data =      self._enc_multiclk_ctl(),
                                 name =      "x393_multiclk_ctl", typ="rw",
                                 frmt_spcs = frmt_spcs)
        stypedefs += self.get_typedef32(comment =   "MULTICLK status",
                                 data =      self._enc_multiclk_status(),
                                 name =      "x393_multiclk_status", typ="ro",
                                 frmt_spcs = frmt_spcs)

        stypedefs += self.get_typedef32(comment =   "DEBUG status",
                                 data =      self._enc_debug_status(),
                                 name =      "x393_debug_status", typ="ro",
                                 frmt_spcs = frmt_spcs)
        
587 588 589 590 591 592
        return stypedefs
    
    def define_macros(self):
        #memory arbiter priorities
        ba = vrlg.CONTROL_ADDR
        z3= (0,3)
593
        z7 = (0,7)
594
        z14= (0,14)
595
        z15= (0,15)
596
        z31= (0,31)
597 598 599 600 601
        ia = 1
        c = "chn"
        sdefines = []
        sdefines +=[
            (('R/W addresses to set up memory arbiter priorities. For sensors  (chn = 8..11), for compressors - 12..15',)),
602
            (("X393_MCNTRL_ARBITER_PRIORITY",              c, vrlg.MCONTR_ARBIT_ADDR +             ba, ia, z15, "x393_arbite_pri", "rw",                     "Set memory arbiter priority (currently r/w, may become just wo)"))]        
603 604 605

        sdefines +=[
            (('Enable/disable memory channels (bits in a 16-bit word). For sensors  (chn = 8..11), for compressors - 12..15',)),
606 607 608
            (("X393_MCNTRL_CHN_EN",     c, vrlg.MCONTR_TOP_16BIT_ADDR +  vrlg.MCONTR_TOP_16BIT_CHN_EN +    ba,     0, None, "x393_mcntr_chn_en", "rw",   "Enable/disable memory channels (currently r/w, may become just wo)")),
            (("X393_MCNTRL_DQS_DQM_PATT",c, vrlg.MCONTR_PHY_16BIT_ADDR+  vrlg.MCONTR_PHY_16BIT_PATTERNS +  ba,     0, None, "x393_mcntr_dqs_dqm_patt", "rw",     "Setup DQS and DQM patterns")),
            (("X393_MCNTRL_DQ_DQS_TRI", c, vrlg.MCONTR_PHY_16BIT_ADDR +  vrlg.MCONTR_PHY_16BIT_PATTERNS_TRI+ ba,   0, None, "x393_mcntr_dqs_dqm_tri", "rw",      "Setup DQS and DQ on/off sequence")),
609
            (("Following enable/disable addresses can be written with any data, only addresses matter",)),
610 611 612 613 614 615 616 617 618 619
            (("X393_MCNTRL_DIS",        c, vrlg.MCONTR_TOP_0BIT_ADDR +   vrlg.MCONTR_TOP_0BIT_MCONTR_EN +  ba + 0, 0, None, "","",                       "Disable DDR3 memory controller")),        
            (("X393_MCNTRL_EN",         c, vrlg.MCONTR_TOP_0BIT_ADDR +   vrlg.MCONTR_TOP_0BIT_MCONTR_EN +  ba + 1, 0, None, "","",                       "Enable DDR3 memory controller")),        
            (("X393_MCNTRL_REFRESH_DIS",c, vrlg.MCONTR_TOP_0BIT_ADDR +   vrlg.MCONTR_TOP_0BIT_REFRESH_EN + ba + 0, 0, None, "","",                       "Disable DDR3 memory refresh")),        
            (("X393_MCNTRL_REFRESH_EN", c, vrlg.MCONTR_TOP_0BIT_ADDR +   vrlg.MCONTR_TOP_0BIT_REFRESH_EN + ba + 1, 0, None, "","",                       "Enable DDR3 memory refresh")),        
            (("X393_MCNTRL_SDRST_DIS",  c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_SDRST_ACT +  ba + 0, 0, None, "","",                       "Disable DDR3 memory reset")),        
            (("X393_MCNTRL_SDRST_EN",   c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_SDRST_ACT +  ba + 1, 0, None, "","",                       "Enable DDR3 memory reset")),        
            (("X393_MCNTRL_CKE_DIS",    c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_CKE_EN +     ba + 0, 0, None, "","",                       "Disable DDR3 memory CKE")),        
            (("X393_MCNTRL_CKE_EN",     c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_CKE_EN +     ba + 1, 0, None, "","",                       "Enable DDR3 memory CKE")),        
            (("X393_MCNTRL_CMDA_DIS",   c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_CMDA_EN +    ba + 0, 0, None, "","",                       "Disable DDR3 memory command/address lines")),        
            (("X393_MCNTRL_CMDA_EN",    c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_CMDA_EN +    ba + 1, 0, None, "","",                       "Enable DDR3 memory command/address lines")),        
620 621 622 623 624
            ]        
        ba = vrlg.CONTROL_ADDR
        #"x393_dly_rw"
        sdefines +=[
            (('Set DDR3 memory controller I/O delays and other timing parameters (should use individually calibrated values)',)),
625 626 627 628 629 630 631 632 633 634 635
            (("X393_MCNTRL_DQ_ODLY0",   c, vrlg.LD_DLY_LANE0_ODELAY +    ba,     1, z7,   "x393_dly", "rw",    "Lane0 DQ output delays ")),
            (("X393_MCNTRL_DQ_ODLY1",   c, vrlg.LD_DLY_LANE1_ODELAY +    ba,     1, z7,   "x393_dly", "rw",    "Lane1 DQ output delays ")),
            (("X393_MCNTRL_DQ_IDLY0",   c, vrlg.LD_DLY_LANE0_IDELAY +    ba,     1, z7,   "x393_dly", "rw",    "Lane0 DQ input delays ")),
            (("X393_MCNTRL_DQ_IDLY1",   c, vrlg.LD_DLY_LANE1_IDELAY +    ba,     1, z7,   "x393_dly", "rw",    "Lane1 DQ input delays ")),
            (("X393_MCNTRL_DQS_ODLY0",  c, vrlg.LD_DLY_LANE0_ODELAY +    ba + 8, 0, None, "x393_dly", "rw",    "Lane0 DQS output delay ")),
            (("X393_MCNTRL_DQS_ODLY1",  c, vrlg.LD_DLY_LANE1_ODELAY +    ba + 8, 0, None, "x393_dly", "rw",    "Lane1 DQS output delay ")),
            (("X393_MCNTRL_DQS_IDLY0",  c, vrlg.LD_DLY_LANE0_IDELAY +    ba + 8, 0, None, "x393_dly", "rw",    "Lane0 DQS input delay ")),
            (("X393_MCNTRL_DQS_IDLY1",  c, vrlg.LD_DLY_LANE1_IDELAY +    ba + 8, 0, None, "x393_dly", "rw",    "Lane1 DQS input delay ")),
            (("X393_MCNTRL_DM_ODLY0",   c, vrlg.LD_DLY_LANE0_ODELAY +    ba + 9, 0, None, "x393_dly", "rw",    "Lane0 DM output delay ")),
            (("X393_MCNTRL_DM_ODLY1",   c, vrlg.LD_DLY_LANE1_ODELAY +    ba + 9, 0, None, "x393_dly", "rw",    "Lane1 DM output delay ")),
            (("X393_MCNTRL_CMDA_ODLY",  c, vrlg.LD_DLY_CMDA +            ba,     1, z31,  "x393_dly", "rw",    "Address, bank and commands delays")),
Andrey Filippov's avatar
Andrey Filippov committed
636
            (("X393_MCNTRL_PHASE",      c, vrlg.LD_DLY_PHASE +           ba,     0, None, "x393_dly", "rw",    "Clock phase")),
637 638
            (("X393_MCNTRL_DLY_SET",    c, vrlg.MCONTR_PHY_0BIT_ADDR +   vrlg.MCONTR_PHY_0BIT_DLY_SET +      ba, 0, None, "", "",             "Set all pre-programmed delays")),
            (("X393_MCNTRL_WBUF_DLY",   c, vrlg.MCONTR_PHY_16BIT_ADDR +  vrlg.MCONTR_PHY_16BIT_WBUF_DELAY +  ba, 0, None, "x393_wbuf_dly", "rw", "Set write buffer delay")),
639 640 641 642 643 644
            ]        
        ba = vrlg.MCONTR_SENS_BASE
        ia = vrlg.MCONTR_SENS_INC
        c = "chn"
        sdefines +=[
            (('Write-only addresses to program memory channels for sensors  (chn = 0..3), memory channels 8..11',)),
645
            (("X393_SENS_MCNTRL_SCANLINE_MODE",            c, vrlg.MCNTRL_SCANLINE_MODE +             ba, ia, z3, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
646
            (("X393_SENS_MCNTRL_SCANLINE_STATUS_CNTRL",    c, vrlg.MCNTRL_SCANLINE_STATUS_CNTRL +     ba, ia, z3, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
647 648 649 650 651 652 653
            (("X393_SENS_MCNTRL_SCANLINE_STARTADDR",       c, vrlg.MCNTRL_SCANLINE_STARTADDR +        ba, ia, z3, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_SENS_MCNTRL_SCANLINE_FRAME_SIZE",      c, vrlg.MCNTRL_SCANLINE_FRAME_SIZE +       ba, ia, z3, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_SENS_MCNTRL_SCANLINE_FRAME_LAST",      c, vrlg.MCNTRL_SCANLINE_FRAME_LAST +       ba, ia, z3, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_SENS_MCNTRL_SCANLINE_FRAME_FULL_WIDTH",c, vrlg.MCNTRL_SCANLINE_FRAME_FULL_WIDTH + ba, ia, z3, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_SENS_MCNTRL_SCANLINE_WINDOW_WH",       c, vrlg.MCNTRL_SCANLINE_WINDOW_WH +        ba, ia, z3, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_SENS_MCNTRL_SCANLINE_WINDOW_X0Y0",     c, vrlg.MCNTRL_SCANLINE_WINDOW_X0Y0 +      ba, ia, z3, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_SENS_MCNTRL_SCANLINE_STARTXY",         c, vrlg.MCNTRL_SCANLINE_WINDOW_STARTXY +   ba, ia, z3, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register"))]
654 655 656 657
        ba = vrlg.MCONTR_CMPRS_BASE
        ia = vrlg.MCONTR_CMPRS_INC
        sdefines +=[
            (('Write-only addresses to program memory channels for compressors (chn = 0..3), memory channels 12..15',)),
658
            (("X393_SENS_MCNTRL_TILED_MODE",               c, vrlg.MCNTRL_TILED_MODE +                ba, ia, z3, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
659
            (("X393_SENS_MCNTRL_TILED_STATUS_CNTRL",       c, vrlg.MCNTRL_TILED_STATUS_CNTRL +        ba, ia, z3, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
660 661 662 663 664 665 666 667
            (("X393_SENS_MCNTRL_TILED_STARTADDR",          c, vrlg.MCNTRL_TILED_STARTADDR +           ba, ia, z3, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_SENS_MCNTRL_TILED_FRAME_SIZE",         c, vrlg.MCNTRL_TILED_FRAME_SIZE +          ba, ia, z3, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_SENS_MCNTRL_TILED_FRAME_LAST",         c, vrlg.MCNTRL_TILED_FRAME_LAST +          ba, ia, z3, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_SENS_MCNTRL_TILED_FRAME_FULL_WIDTH",   c, vrlg.MCNTRL_TILED_FRAME_FULL_WIDTH +    ba, ia, z3, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_SENS_MCNTRL_TILED_WINDOW_WH",          c, vrlg.MCNTRL_TILED_WINDOW_WH +           ba, ia, z3, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_SENS_MCNTRL_TILED_WINDOW_X0Y0",        c, vrlg.MCNTRL_TILED_WINDOW_X0Y0 +         ba, ia, z3, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_SENS_MCNTRL_TILED_STARTXY",            c, vrlg.MCNTRL_TILED_WINDOW_STARTXY +      ba, ia, z3, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register")),
            (("X393_SENS_MCNTRL_TILED_TILE_WHS",           c, vrlg.MCNTRL_TILED_TILE_WHS +            ba, ia, z3, "x393_mcntrl_window_tile_whs", "wo",       "Set tile size/step (tiled mode only)"))]
668 669 670 671 672 673

        ba = vrlg.MCNTRL_SCANLINE_CHN1_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('Write-only addresses to program memory channel for membridge, memory channel 1',)),
674
            (("X393_MEMBRIDGE_SCANLINE_MODE",            c, vrlg.MCNTRL_SCANLINE_MODE +             ba, 0, None, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
675
            (("X393_MEMBRIDGE_SCANLINE_STATUS_CNTRL",    c, vrlg.MCNTRL_SCANLINE_STATUS_CNTRL +     ba, 0, None, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
676 677 678 679 680 681 682
            (("X393_MEMBRIDGE_SCANLINE_STARTADDR",       c, vrlg.MCNTRL_SCANLINE_STARTADDR +        ba, 0, None, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_MEMBRIDGE_SCANLINE_FRAME_SIZE",      c, vrlg.MCNTRL_SCANLINE_FRAME_SIZE +       ba, 0, None, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_MEMBRIDGE_SCANLINE_FRAME_LAST",      c, vrlg.MCNTRL_SCANLINE_FRAME_LAST +       ba, 0, None, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_MEMBRIDGE_SCANLINE_FRAME_FULL_WIDTH",c, vrlg.MCNTRL_SCANLINE_FRAME_FULL_WIDTH + ba, 0, None, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_MEMBRIDGE_SCANLINE_WINDOW_WH",       c, vrlg.MCNTRL_SCANLINE_WINDOW_WH +        ba, 0, None, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_MEMBRIDGE_SCANLINE_WINDOW_X0Y0",     c, vrlg.MCNTRL_SCANLINE_WINDOW_X0Y0 +      ba, 0, None, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_MEMBRIDGE_SCANLINE_STARTXY",         c, vrlg.MCNTRL_SCANLINE_WINDOW_STARTXY +   ba, 0, None, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register"))]
683 684 685 686 687
        
        ba = vrlg.MEMBRIDGE_ADDR
        ia = 0
        c =  ""
        sdefines +=[
688
            (("X393_MEMBRIDGE_CTRL",                     c, vrlg.MEMBRIDGE_CTRL +                  ba, 0, None, "x393_membridge_cmd", "wo",                "Issue membridge command")),
689
            (("X393_MEMBRIDGE_STATUS_CNTRL",             c, vrlg.MEMBRIDGE_STATUS_CNTRL +          ba, 0, None, "x393_status_ctrl", "rw",                  "Set membridge status control register")),
690 691 692 693 694 695
            (("X393_MEMBRIDGE_LO_ADDR64",                c, vrlg.MEMBRIDGE_LO_ADDR64 +             ba, 0, None, "u29", "wo",                               "start address of the system memory range in QWORDs (4 LSBs==0)")),
            (("X393_MEMBRIDGE_SIZE64",                   c, vrlg.MEMBRIDGE_SIZE64 +                ba, 0, None, "u29", "wo",                               "size of the system memory range in QWORDs (4 LSBs==0), rolls over")),
            (("X393_MEMBRIDGE_START64",                  c, vrlg.MEMBRIDGE_START64 +               ba, 0, None, "u29", "wo",                               "start of transfer offset to system memory range in QWORDs (4 LSBs==0)")),
            (("X393_MEMBRIDGE_LEN64",                    c, vrlg.MEMBRIDGE_LEN64 +                 ba, 0, None, "u29", "wo",                               "Full length of transfer in QWORDs")),
            (("X393_MEMBRIDGE_WIDTH64",                  c, vrlg.MEMBRIDGE_WIDTH64 +               ba, 0, None, "u29", "wo",                               "Frame width in QWORDs (last xfer in each line may be partial)")),
            (("X393_MEMBRIDGE_MODE",                     c, vrlg.MEMBRIDGE_MODE +                  ba, 0, None, "x393_membridge_mode", "wo",               "AXI cache mode"))]
696 697 698 699 700 701

        ba = vrlg.MCNTRL_PS_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('Write-only addresses to PS PIO (Software generated DDR3 memory access sequences)',)),
702 703
            (("X393_MCNTRL_PS_EN_RST",                   c, vrlg.MCNTRL_PS_EN_RST +                ba, 0, None, "x393_ps_pio_en_rst", "wo",                 "Set PS PIO enable and reset")),
            (("X393_MCNTRL_PS_CMD",                      c, vrlg.MCNTRL_PS_CMD +                   ba, 0, None, "x393_ps_pio_cmd", "wo",                    "Set PS PIO commands")),
704
            (("X393_MCNTRL_PS_STATUS_CNTRL",             c, vrlg.MCNTRL_PS_STATUS_CNTRL +          ba, 0, None, "x393_status_ctrl", "rw",                   "Set PS PIO status control register (status update mode)"))]
705 706 707 708 709 710

        #other program status (move to other places?)
        ba = vrlg.MCONTR_PHY_16BIT_ADDR
        ia = 0
        c =  ""
        sdefines +=[
711
            (('Write-only addresses to to program status report mode for memory controller',)),
712 713
            (("X393_MCONTR_PHY_STATUS_CNTRL",            c, vrlg.MCONTR_PHY_STATUS_CNTRL +         ba, 0, None, "x393_status_ctrl", "rw",                    "Set status control register (status update mode)")),
            (("X393_MCONTR_TOP_16BIT_STATUS_CNTRL",      c, vrlg.MCONTR_TOP_16BIT_STATUS_CNTRL +   ba, 0, None, "x393_status_ctrl", "rw",                    "Set status control register (status update mode)")),
714 715 716 717 718 719
        ]
        ba = vrlg.MCNTRL_TEST01_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('Write-only addresses to to program status report mode for test channels',)),
720 721 722
            (("X393_MCNTRL_TEST01_CHN2_STATUS_CNTRL",    c, vrlg.MCNTRL_TEST01_CHN2_STATUS_CNTRL + ba, 0, None, "x393_status_ctrl", "rw",                    "Set status control register (status update mode)")),
            (("X393_MCNTRL_TEST01_CHN3_STATUS_CNTRL",    c, vrlg.MCNTRL_TEST01_CHN3_STATUS_CNTRL + ba, 0, None, "x393_status_ctrl", "rw",                    "Set status control register (status update mode)")),
            (("X393_MCNTRL_TEST01_CHN4_STATUS_CNTRL",    c, vrlg.MCNTRL_TEST01_CHN4_STATUS_CNTRL + ba, 0, None, "x393_status_ctrl", "rw",                    "Set status control register (status update mode)")),
723
            (('Write-only addresses for test channels commands',)),
724 725 726
            (("X393_MCNTRL_TEST01_CHN2_MODE",            c, vrlg.MCNTRL_TEST01_CHN2_MODE +         ba, 0, None, "x393_test01_mode", "wo",                    "Set command for test01 channel 2")),
            (("X393_MCNTRL_TEST01_CHN3_MODE",            c, vrlg.MCNTRL_TEST01_CHN3_MODE +         ba, 0, None, "x393_test01_mode", "wo",                    "Set command for test01 channel 3")),
            (("X393_MCNTRL_TEST01_CHN4_MODE",            c, vrlg.MCNTRL_TEST01_CHN4_MODE +         ba, 0, None, "x393_test01_mode", "wo",                    "Set command for test01 channel 4")),
727 728 729 730 731 732 733 734
            
]
        #read_all_status
        ba = vrlg.STATUS_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('Read-only addresses for status information',)),
735 736 737 738 739 740 741 742 743 744 745
            (("X393_MCONTR_PHY_STATUS",                  c, vrlg.MCONTR_PHY_STATUS_REG_ADDR + ba, 0, None, "x393_status_mcntrl_phy", "ro",                   "Status register for MCNTRL PHY")),
            (("X393_MCONTR_TOP_STATUS",                  c, vrlg.MCONTR_TOP_STATUS_REG_ADDR + ba, 0, None, "x393_status_mcntrl_top", "ro",                   "Status register for MCNTRL requests")),
            (("X393_MCNTRL_PS_STATUS",                   c, vrlg.MCNTRL_PS_STATUS_REG_ADDR +  ba, 0, None, "x393_status_mcntrl_ps", "ro",                    "Status register for MCNTRL software R/W")),
            (("X393_MCNTRL_CHN1_STATUS",                 c, vrlg.MCNTRL_SCANLINE_STATUS_REG_CHN1_ADDR+ba,0,None, "x393_status_mcntrl_lintile", "ro",         "Status register for MCNTRL CHN1 (membridge)")),
            (("X393_MCNTRL_CHN3_STATUS",                 c, vrlg.MCNTRL_SCANLINE_STATUS_REG_CHN3_ADDR+ba,0,None, "x393_status_mcntrl_lintile", "ro",         "Status register for MCNTRL CHN3 (scanline)")),
            (("X393_MCNTRL_CHN2_STATUS",                 c, vrlg.MCNTRL_TILED_STATUS_REG_CHN2_ADDR+ba,0,None,    "x393_status_mcntrl_lintile", "ro",         "Status register for MCNTRL CHN2 (tiled)")),
            (("X393_MCNTRL_CHN4_STATUS",                 c, vrlg.MCNTRL_TILED_STATUS_REG_CHN4_ADDR+ba,0,None,    "x393_status_mcntrl_lintile", "ro",         "Status register for MCNTRL CHN4 (tiled)")),
            (("X393_TEST01_CHN2_STATUS",                 c, vrlg.MCNTRL_TEST01_STATUS_REG_CHN2_ADDR+ba,0,None,   "x393_status_mcntrl_testchn", "ro",         "Status register for test channel 2")),
            (("X393_TEST01_CHN3_STATUS",                 c, vrlg.MCNTRL_TEST01_STATUS_REG_CHN3_ADDR+ba,0,None,   "x393_status_mcntrl_testchn", "ro",         "Status register for test channel 3")),
            (("X393_TEST01_CHN4_STATUS",                 c, vrlg.MCNTRL_TEST01_STATUS_REG_CHN4_ADDR+ba,0,None,   "x393_status_mcntrl_testchn", "ro",         "Status register for test channel 4")),
            (("X393_MEMBRIDGE_STATUS",                   c, vrlg.MEMBRIDGE_STATUS_REG+ba, 0, None,         "x393_status_membridge", "ro",                    "Status register for membridge")),
746 747 748 749 750 751 752 753
            ]

        #Registers to control sensor channels        
        ba = vrlg.SENSOR_GROUP_ADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "sens_num"
        sdefines +=[
            (('Write-only control of the sensor channels',)),
754 755
            (("X393_SENS_MODE",                         c, vrlg.SENSOR_CTRL_RADDR +                        ba, ia, z3, "x393_sens_mode", "wo",               "Write sensor channel mode")),
            (("X393_SENSI2C_CTRL",                      c, vrlg.SENSI2C_CTRL_RADDR + vrlg.SENSI2C_CTRL +   ba, ia, z3, "x393_i2c_ctltbl", "wo",              "Control sensor i2c, write i2c LUT")),
756
            (("X393_SENSI2C_STATUS_CTRL",               c, vrlg.SENSI2C_CTRL_RADDR + vrlg.SENSI2C_STATUS + ba, ia, z3, "x393_status_ctrl", "rw",             "Setup sensor i2c status report mode")),
757 758 759 760
            (("X393_SENS_SYNC_MULT",                    c, vrlg.SENS_SYNC_RADDR + vrlg.SENS_SYNC_MULT +    ba, ia, z3, "x393_sens_sync_mult", "wo",          "Configure frames combining")),
            (("X393_SENS_SYNC_LATE",                    c, vrlg.SENS_SYNC_RADDR + vrlg.SENS_SYNC_LATE +    ba, ia, z3, "x393_sens_sync_late", "wo",          "Configure frame sync delay")),
            (("X393_SENSIO_CTRL",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_CTRL +          ba, ia, z3, "x393_sensio_ctl", "wo",              "Configure sensor I/O port")),
            (("X393_SENSIO_STATUS_CNTRL",               c, vrlg.SENSIO_RADDR + vrlg.SENSIO_STATUS +        ba, ia, z3, "x393_status_ctrl", "rw",             "Set status control for SENSIO module")),
761
            (("X393_SENSIO_JTAG",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_JTAG +          ba, ia, z3, "x393_sensio_jtag", "wo",             "Programming interface for multiplexer FPGA (with X393_SENSIO_STATUS)")),
762 763 764 765 766 767
            (("X393_SENSIO_WIDTH",                      c, vrlg.SENSIO_RADDR + vrlg.SENSIO_WIDTH +         ba, ia, z3, "x393_sensio_width", "rw",            "Set sensor line in pixels (0 - use line sync from the sensor)")),
#            (("X393_SENSIO_DELAYS",                     c, vrlg.SENSIO_RADDR + vrlg.SENSIO_DELAYS +       ba, ia, z3, "x393_sensio_dly", "rw",              "Sensor port input delays (uses 4 DWORDs)")),
            (("X393_SENSIO_TIM0",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_DELAYS + 0 +    ba, ia, z3, "x393_sensio_tim0", "rw",             "Sensor port i/o timing configuration, register 0")),
            (("X393_SENSIO_TIM1",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_DELAYS + 1 +    ba, ia, z3, "x393_sensio_tim1", "rw",             "Sensor port i/o timing configuration, register 1")),
            (("X393_SENSIO_TIM2",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_DELAYS + 2 +    ba, ia, z3, "x393_sensio_tim2", "rw",             "Sensor port i/o timing configuration, register 2")),
            (("X393_SENSIO_TIM3",                       c, vrlg.SENSIO_RADDR + vrlg.SENSIO_DELAYS + 3 +    ba, ia, z3, "x393_sensio_tim3", "rw",             "Sensor port i/o timing configuration, register 3")),
768
            ]
769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787
        #Registers to control sensor channels        
        ba = vrlg.SENSOR_GROUP_ADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "sens_num"
        sdefines +=[
            (('''I2C command sequencer, block of 16 DWORD slots for absolute frame numbers (modulo 16) and 15 slots for relative ones
// 0 - ASAP, 1 next frame, 14 -14-th next.
// Data written depends on context:
// 1 - I2C register write: index page (MSB), 3 payload bytes. Payload bytes are used according to table and sent
//     after the slave address and optional high address byte. Other bytes are sent in descending order (LSB- last).
//     If less than 4 bytes are programmed in the table the high bytes (starting with the one from the table) are
//     skipped.
//     If more than 4 bytes are programmed in the table for the page (high byte), one or two next 32-bit words 
//     bypass the index table and all 4 bytes are considered payload ones. If less than 4 extra bytes are to be
//     sent for such extra word, only the lower bytes are sent.
//
// 2 - I2C register read: index page, slave address (8-bit, with lower bit 0) and one or 2 address bytes (as programmed
//     in the table. Slave address is always in byte 2 (bits 23:16), byte1 (high register address) is skipped if
//     read address in the table is programmed to be a single-byte one''',)),
788 789
            (("X393_SENSI2C_ABS",            (c,"offset"), vrlg.SENSI2C_ABS_RADDR +                      ba, (ia,1), (z3,z15), "u32*", "wo",                 "Write sensor i2c sequencer")),
            (("X393_SENSI2C_REL",            (c,"offset"), vrlg.SENSI2C_REL_RADDR +                      ba, (ia,1), (z3,z15), "u32*", "wo",                 "Write sensor i2c sequencer"))]
790 791 792 793 794 795 796
        
        #Lens vignetting correction
        ba = vrlg.SENSOR_GROUP_ADDR + vrlg.SENS_LENS_RADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "sens_num"
        sdefines +=[
            (('Lens vignetting correction (for each sub-frame separately)',)),
797 798 799 800
            (("X393_LENS_HEIGHT0_M1",                   c, 0 +                                            ba, ia, z3, "x393_lens_height_m1", "rw",           "Subframe 0 height minus 1")),
            (("X393_LENS_HEIGHT1_M1",                   c, 1 +                                            ba, ia, z3, "x393_lens_height_m1", "rw",           "Subframe 1 height minus 1")),
            (("X393_LENS_HEIGHT2_M1",                   c, 2 +                                            ba, ia, z3, "x393_lens_height_m1", "rw",           "Subframe 2 height minus 1")),
            (("X393_LENS_CORR_CNH_ADDR_DATA",           c, vrlg.SENS_LENS_COEFF +                         ba, ia, z3, "x393_lens_corr", "wo",                "Combined address/data to write lens vignetting correction coefficients")),
801
            (('Lens vignetting coefficient addresses - use with x393_lens_corr_wo_t (X393_LENS_CORR_CNH_ADDR_DATA)',)),
802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822
            (("X393_LENS_AX",             "", vrlg.SENS_LENS_AX ,             0, None, None, "",    "Address of correction parameter Ax")),
            (("X393_LENS_AX_MASK",        "", vrlg.SENS_LENS_AX_MASK ,        0, None, None, "",    "Correction parameter Ax mask")),
            (("X393_LENS_AY",             "", vrlg.SENS_LENS_AY ,             0, None, None, "",    "Address of correction parameter Ay")),
            (("X393_LENS_AY_MASK",        "", vrlg.SENS_LENS_AY_MASK ,        0, None, None, "",    "Correction parameter Ay mask")),
            (("X393_LENS_C",              "", vrlg.SENS_LENS_C ,              0, None, None, "",    "Address of correction parameter C")),
            (("X393_LENS_C_MASK",         "", vrlg.SENS_LENS_C_MASK ,         0, None, None, "",    "Correction parameter C mask")),
            (("X393_LENS_BX",             "", vrlg.SENS_LENS_BX ,             0, None, None, "",    "Address of correction parameter Bx")),
            (("X393_LENS_BX_MASK",        "", vrlg.SENS_LENS_BX_MASK ,        0, None, None, "",    "Correction parameter Bx mask")),
            (("X393_LENS_BY",             "", vrlg.SENS_LENS_BY ,             0, None, None, "",    "Address of correction parameter By")),
            (("X393_LENS_BY_MASK",        "", vrlg.SENS_LENS_BY_MASK ,        0, None, None, "",    "Correction parameter By mask")),
            (("X393_LENS_SCALE0",         "", vrlg.SENS_LENS_SCALES ,         0, None, None, "",    "Address of correction parameter scale0")),
            (("X393_LENS_SCALE1",         "", vrlg.SENS_LENS_SCALES + 2 ,     0, None, None, "",    "Address of correction parameter scale1")),
            (("X393_LENS_SCALE2",         "", vrlg.SENS_LENS_SCALES + 4 ,     0, None, None, "",    "Address of correction parameter scale2")),
            (("X393_LENS_SCALE3",         "", vrlg.SENS_LENS_SCALES + 6 ,     0, None, None, "",    "Address of correction parameter scale3")),
            (("X393_LENS_SCALES_MASK",    "", vrlg.SENS_LENS_SCALES_MASK ,    0, None, None, "",    "Common mask for scales")),
            (("X393_LENS_FAT0_IN",        "", vrlg.SENS_LENS_FAT0_IN ,        0, None, None, "",    "Address of input fat zero parameter (to subtract from input)")),
            (("X393_LENS_FAT0_IN_MASK",   "", vrlg.SENS_LENS_FAT0_IN_MASK ,   0, None, None, "",    "Mask for fat zero input parameter")),
            (("X393_LENS_FAT0_OUT",       "", vrlg.SENS_LENS_FAT0_OUT,        0, None, None, "",    "Address of output fat zero parameter (to add to output)")),
            (("X393_LENS_FAT0_OUT_MASK",  "", vrlg.SENS_LENS_FAT0_OUT_MASK ,  0, None, None, "",    "Mask for fat zero output  parameters")),
            (("X393_LENS_POST_SCALE",     "", vrlg.SENS_LENS_POST_SCALE ,     0, None, None, "",    "Address of post scale (shift output) parameter")),
            (("X393_LENS_POST_SCALE_MASK","", vrlg.SENS_LENS_POST_SCALE_MASK, 0, None, None, "",    "Mask for post scale parameter"))]
823 824 825 826 827 828
        #Gamma tables (See Python code for examples of the table data generation)
        ba = vrlg.SENSOR_GROUP_ADDR + vrlg.SENS_GAMMA_RADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "sens_num"
        sdefines +=[
            (('Sensor gamma conversion control (See Python code for examples of the table data generation)',)),
829 830 831 832
            (("X393_SENS_GAMMA_CTRL",                   c, vrlg.SENS_GAMMA_CTRL +                          ba, ia, z3, "x393_gamma_ctl", "rw",               "Gamma module control")),
            (("X393_SENS_GAMMA_TBL",                    c, vrlg.SENS_GAMMA_ADDR_DATA +                     ba, ia, z3, "x393_gamma_tbl", "wo",               "Write sensor gamma table address/data (with autoincrement)")),
            (("X393_SENS_GAMMA_HEIGHT01M1",             c, vrlg.SENS_GAMMA_HEIGHT01 +                      ba, ia, z3, "x393_gamma_height01m1", "rw",        "Gamma module subframes 0,1 heights minus 1")),
            (("X393_SENS_GAMMA_HEIGHT2M1",              c, vrlg.SENS_GAMMA_HEIGHT2 +                       ba, ia, z3, "x393_gamma_height2m1", "rw",         "Gamma module subframe  2 height minus 1"))]
833 834 835 836 837 838 839

        #Histogram window controls
        ba = vrlg.SENSOR_GROUP_ADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "sens_num"
        sdefines +=[
            (('Windows for histogram subchannels',)),
840 841 842 843 844 845 846 847
            (("X393_HISTOGRAM_LT0",                     c, vrlg.HISTOGRAM_RADDR0 +                         ba, ia, z3, "x393_hist_left_top", "rw",          "Specify histogram 0 left/top")),
            (("X393_HISTOGRAM_WH0",                     c, vrlg.HISTOGRAM_RADDR0 + 1 +                     ba, ia, z3, "x393_hist_width_height_m1", "rw",   "Specify histogram 0 width/height")),
            (("X393_HISTOGRAM_LT1",                     c, vrlg.HISTOGRAM_RADDR1 +                         ba, ia, z3, "x393_hist_left_top", "rw",          "Specify histogram 1 left/top")),
            (("X393_HISTOGRAM_WH1",                     c, vrlg.HISTOGRAM_RADDR1 + 1 +                     ba, ia, z3, "x393_hist_width_height_m1", "rw",   "Specify histogram 1 width/height")),
            (("X393_HISTOGRAM_LT2",                     c, vrlg.HISTOGRAM_RADDR2 +                         ba, ia, z3, "x393_hist_left_top", "rw",          "Specify histogram 2 left/top")),
            (("X393_HISTOGRAM_WH2",                     c, vrlg.HISTOGRAM_RADDR2 + 1 +                     ba, ia, z3, "x393_hist_width_height_m1", "rw",   "Specify histogram 2 width/height")),
            (("X393_HISTOGRAM_LT3",                     c, vrlg.HISTOGRAM_RADDR3 +                         ba, ia, z3, "x393_hist_left_top", "rw",          "Specify histogram 3 left/top")),
            (("X393_HISTOGRAM_WH3",                     c, vrlg.HISTOGRAM_RADDR3 + 1 +                     ba, ia, z3, "x393_hist_width_height_m1", "rw",   "Specify histogram 3 width/height"))]        
848 849 850 851 852
        ba = vrlg.SENSOR_GROUP_ADDR
        ia = vrlg.SENSOR_BASE_INC
        c =  "subchannel"
        sdefines +=[
            (('DMA control for the histograms. Subchannel here is 4*sensor_port+ histogram_subchannel',)),
853 854
            (("X393_HIST_SAXI_MODE",                    c, vrlg.HIST_SAXI_MODE_ADDR_REL +                  ba,  0, None, "x393_hist_saxi_mode", "rw",       "Histogram DMA operation mode")),
            (("X393_HIST_SAXI_ADDR",                    c, vrlg.HIST_SAXI_ADDR_REL +                       ba,  1, z15,  "x393_hist_saxi_addr", "rw",       "Histogram DMA addresses (in 4096 byte pages)"))]
855 856 857 858 859 860 861 862 863
        #sensors status        
        ba = vrlg.STATUS_ADDR + vrlg.SENSI2C_STATUS_REG_BASE
        ia = vrlg.SENSI2C_STATUS_REG_INC
        c =  "sens_num"
        sdefines +=[
            (('Read-only addresses for sensors status information',)),
            (("X393_SENSI2C_STATUS",                    c, vrlg.SENSI2C_STATUS_REG_REL +      ba, ia, z3, "x393_status_sens_i2c", "ro",                       "Status of the sensors i2c")),
            (("X393_SENSIO_STATUS",                     c, vrlg.SENSIO_STATUS_REG_REL +       ba, ia, z3, "x393_status_sens_io", "ro",                        "Status of the sensor ports I/O pins")),
            ]
864

865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891
        #Compressor control
        sdefines +=[
            (('Compressor bitfields values',)),
            (("X393_CMPRS_CBIT_RUN_RST",            "", vrlg.CMPRS_CBIT_RUN_RST ,           0, None, None, "", "Reset compressor, stop immediately")),
            (("X393_CMPRS_CBIT_RUN_DISABLE",        "", 1 ,                                 0, None, None, "", "Disable compression of the new frames, finish any already started")),
            (("X393_CMPRS_CBIT_RUN_STANDALONE",     "", vrlg.CMPRS_CBIT_RUN_STANDALONE ,    0, None, None, "", "Enable compressor, compress single frame from memory (async)")),
            (("X393_CMPRS_CBIT_RUN_ENABLE",         "", vrlg.CMPRS_CBIT_RUN_ENABLE ,        0, None, None, "", "Enable synchronous compression mode")),

            (("X393_CMPRS_CBIT_CMODE_JPEG18",       "", vrlg.CMPRS_CBIT_CMODE_JPEG18 ,      0, None, None, "", "Color 4:2:0 3x3 de-bayer core")),
            (("X393_CMPRS_CBIT_CMODE_MONO6",        "", vrlg.CMPRS_CBIT_CMODE_MONO6 ,       0, None, None, "", "Mono 4:2:0 (6 blocks)")),
            (("X393_CMPRS_CBIT_CMODE_JP46",         "", vrlg.CMPRS_CBIT_CMODE_JP46 ,        0, None, None, "", "jp4, 6 blocks, original")),
            (("X393_CMPRS_CBIT_CMODE_JP46DC",       "", vrlg.CMPRS_CBIT_CMODE_JP46DC ,      0, None, None, "", "jp4, 6 blocks, DC-improved")),
            (("X393_CMPRS_CBIT_CMODE_JPEG20",       "", vrlg.CMPRS_CBIT_CMODE_JPEG20 ,      0, None, None, "", "Color 4:2:0 with 5x5 de-bayer (not implemented)")),
            (("X393_CMPRS_CBIT_CMODE_JP4",          "", vrlg.CMPRS_CBIT_CMODE_JP4 ,         0, None, None, "", "jp4,  4 blocks")),
            (("X393_CMPRS_CBIT_CMODE_JP4DC",        "", vrlg.CMPRS_CBIT_CMODE_JP4DC ,       0, None, None, "", "jp4,  4 blocks, DC-improved")),
            (("X393_CMPRS_CBIT_CMODE_JP4DIFF",      "", vrlg.CMPRS_CBIT_CMODE_JP4DIFF ,     0, None, None, "", "jp4,  4 blocks, differential")),
            (("X393_CMPRS_CBIT_CMODE_JP4DIFFHDR",   "", vrlg.CMPRS_CBIT_CMODE_JP4DIFFHDR,   0, None, None, "", "jp4,  4 blocks, differential, hdr")),
            (("X393_CMPRS_CBIT_CMODE_JP4DIFFDIV2",  "", vrlg.CMPRS_CBIT_CMODE_JP4DIFFDIV2,  0, None, None, "", "jp4,  4 blocks, differential, divide by 2")),
            (("X393_CMPRS_CBIT_CMODE_JP4DIFFHDRDIV2","",vrlg.CMPRS_CBIT_CMODE_JP4DIFFHDRDIV2,0,None, None, "", "jp4,  4 blocks, differential, hdr,divide by 2")),
            (("X393_CMPRS_CBIT_CMODE_MONO1",        "", vrlg.CMPRS_CBIT_CMODE_MONO1 ,       0, None, None, "", "Mono JPEG (not yet implemented)")),
            (("X393_CMPRS_CBIT_CMODE_MONO4",        "", vrlg.CMPRS_CBIT_CMODE_MONO4 ,       0, None, None, "", "Mono, 4 blocks (2x2 macroblocks)")),
            (("X393_CMPRS_CBIT_CMODE_JPEG18",       "", vrlg.CMPRS_CBIT_CMODE_JPEG18 ,      0, None, None, "", "Color 4:2:0")),

            (("X393_CMPRS_CBIT_FRAMES_SINGLE",      "", vrlg.CMPRS_CBIT_FRAMES_SINGLE ,     0, None, None, "", "Use single-frame buffer")),
            (("X393_CMPRS_CBIT_FRAMES_MULTI",       "", 1 ,                                 0, None, None, "", "Use multi-frame buffer"))]        
        ba = vrlg.CMPRS_GROUP_ADDR
        ia = vrlg.CMPRS_BASE_INC
892
        c =  "cmprs_chn"
893 894 895
        sdefines +=[
            (('Compressor control',)),
            (("X393_CMPRS_CONTROL_REG",                  c, vrlg.CMPRS_CONTROL_REG +                  ba, ia, z3, "x393_cmprs_mode", "wo",                    "Program compressor channel operation mode")),
896
            (("X393_CMPRS_STATUS",                       c, vrlg.CMPRS_STATUS_CNTRL +                 ba, ia, z3, "x393_status_ctrl", "rw",                   "Setup compressor status report mode")),
897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922
            (("X393_CMPRS_FORMAT",                       c, vrlg.CMPRS_FORMAT +                       ba, ia, z3, "x393_cmprs_frame_format", "rw",            "Compressor frame format")),
            (("X393_CMPRS_COLOR_SATURATION",             c, vrlg.CMPRS_COLOR_SATURATION +             ba, ia, z3, "x393_cmprs_colorsat", "rw",                "Compressor color saturation")),
            (("X393_CMPRS_CORING_MODE",                  c, vrlg.CMPRS_CORING_MODE +                  ba, ia, z3, "x393_cmprs_coring_mode", "rw",             "Select coring mode")),
            (("X393_CMPRS_INTERRUPTS",                   c, vrlg.CMPRS_INTERRUPTS +                   ba, ia, z3, "x393_cmprs_interrupts", "wo",              "Compressor interrupts control (1 - clear, 2 - disable, 3 - enable)")),
            (('_Compressor tables load control',)),
            (('_Several tables can be loaded to the compressor, there are 4 types of them:',)),
            (('_    0:quantization tables - 8 pairs can be loaded and switched at run time,',)),
            (('_    1:coring tables -       8 pairs can be loaded and switched at run time,',)),
            (('_    2:focusing tables -    15 tables can be loaded and switched at run time (16-th table address space',)),
            (('_      is used to program other focusing mode parameters,',)),
            (('_    3:Huffman tables -     1 pair tables can be loaded',)),
            (('_Default tables are loaded with the bitstream file (100% quality for quantization table 0',)),
            (('_Loading a table requires to load address of the beginning of data, it includes table type and optional offset',)),
            (('_when multiple tables of the same type are used. Next the data should be written to the same register address,',)),
            (('_the table address is auto-incremented,',)),
            (('_Data for the tables 0..2 should be combined: two items into a single 32-bit DWORD (little endian), treating',)),
            (('_each item as a 16-bit word. The Huffman table is one item per DWORD. Address offset is calculated in DWORDs',)),
            (('Compressor table types',)),
            (("X393_TABLE_QUANTIZATION_TYPE",            "", vrlg.TABLE_QUANTIZATION_INDEX ,        0, None, None, "", "Quantization table type")),
            (("X393_TABLE_CORING_TYPE",                  "", vrlg.TABLE_CORING_INDEX ,              0, None, None, "", "Coring table type")),
            (("X393_TABLE_FOCUS_TYPE",                   "", vrlg.TABLE_FOCUS_INDEX ,               0, None, None, "", "Focus table type")),
            (("X393_TABLE_HUFFMAN_TYPE",                 "", vrlg.TABLE_HUFFMAN_INDEX ,             0, None, None, "", "Huffman table type")),
            (('Compressor tables control',)),
            (("X393_CMPRS_TABLES_DATA",                   c, vrlg.CMPRS_TABLES + 0 +                 ba, ia, z3, "u32*", "wo",                               "Compressor tables data")),
            (("X393_CMPRS_TABLES_ADDRESS",                c, vrlg.CMPRS_TABLES + 1 +                 ba, ia, z3, "x393_cmprs_table_addr", "wo",              "Compressor tables type/address")),
             ]
923 924 925 926 927 928 929 930
        ba = vrlg.STATUS_ADDR
        ia = vrlg.CMPRS_STATUS_REG_INC
        c =  "chn"
        sdefines +=[
            (('Compressor channel status)',)),
            (("X393_CMPRS_STATUS",             c, vrlg.CMPRS_STATUS_REG_BASE + ba, vrlg.CMPRS_STATUS_REG_INC, z3, "x393_cmprs_status", "ro",          "Status of the compressor channel (incl. interrupt")),
            (("X393_CMPRS_HIFREQ",             c, vrlg.CMPRS_HIFREQ_REG_BASE + ba, vrlg.CMPRS_HIFREQ_REG_INC, z3, "u32*", "ro",                       "Focus helper high-frequency amount"))]
        
931 932 933
        ba = vrlg.CMPRS_GROUP_ADDR + vrlg.CMPRS_AFIMUX_RADDR0
        ia = 0
        c =  "afi_port"
934
        sdefines +=[
935 936 937 938 939 940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962
            (('Compressor DMA control:',)),
            (('_Camera can be configured to use either 2 AXI HP channels (with 2 compressors served by each one) or to use a single AXI HP channel',)),
            (('_serving all 4 compressor channels through its input ports. Below afi_port (0..3) references to one of the 4 ports of each. Control',)),
            (('_for two AXI HP channels is implemented as separate functions. Currently only the first channel is used',)),
            (("X393_AFIMUX0_EN",                          c, vrlg.CMPRS_AFIMUX_EN +                  ba, 0, None, "x393_afimux_en", "wo",             "AFI MUX 0 global/port run/pause control")),
            (("X393_AFIMUX0_RST",                         c, vrlg.CMPRS_AFIMUX_RST +                 ba, 0, None, "x393_afimux_rst", "rw",            "AFI MUX 0 per-port resets")),
            (("X393_AFIMUX0_REPORT_MODE",                 c, vrlg.CMPRS_AFIMUX_MODE +                ba, 0, None, "x393_afimux_report", "wo",         "AFI MUX 0 readout pointer report mode")),
            (("X393_AFIMUX0_STATUS_CONTROL",              c, vrlg.CMPRS_AFIMUX_STATUS_CNTRL +        ba, 0, None, "x393_status_ctrl", "rw",           "AFI MUX 0 status report mode")),
            (("X393_AFIMUX0_SA",                          c, vrlg.CMPRS_AFIMUX_SA_LEN +              ba, 1, z3,   "x393_afimux_sa", "rw",             "AFI MUX 0 DMA buffer start address in 32-byte blocks")),
            (("X393_AFIMUX0_LEN",                         c, vrlg.CMPRS_AFIMUX_SA_LEN + 4 +          ba, 1, z3,   "x393_afimux_len", "rw",            "AFI MUX 0 DMA buffer length in 32-byte blocks"))]
        ba = vrlg.CMPRS_GROUP_ADDR + vrlg.CMPRS_AFIMUX_RADDR1
        sdefines +=[
            (('_Same for the second AXI HP channel (not currently used)',)),
            (("X393_AFIMUX1_EN",                          c, vrlg.CMPRS_AFIMUX_EN +                  ba, 0, None, "x393_afimux_en", "wo",             "AFI MUX 1 global/port run/pause control")),
            (("X393_AFIMUX1_RST",                         c, vrlg.CMPRS_AFIMUX_RST +                 ba, 0, None, "x393_afimux_rst", "rw",            "AFI MUX 1 per-port resets")),
            (("X393_AFIMUX1_REPORT_MODE",                 c, vrlg.CMPRS_AFIMUX_MODE +                ba, 0, None, "x393_afimux_report", "wo",         "AFI MUX 1 readout pointer report mode")),
            (("X393_AFIMUX1_STATUS_CONTROL",              c, vrlg.CMPRS_AFIMUX_STATUS_CNTRL +        ba, 0, None, "x393_status_ctrl", "rw",           "AFI MUX 1 status report mode")),
            (("X393_AFIMUX1_SA",                          c, vrlg.CMPRS_AFIMUX_SA_LEN +              ba, 1, z3,   "x393_afimux_sa", "rw",             "AFI MUX 1 DMA buffer start address in 32-byte blocks")),
            (("X393_AFIMUX1_LEN",                         c, vrlg.CMPRS_AFIMUX_SA_LEN + 4 +          ba, 1, z3,   "x393_afimux_len", "rw",            "AFI MUX 1 DMA buffer length in 32-byte blocks"))]        

        #compressor DMA status        
        ba = vrlg.STATUS_ADDR
        ia = 1
        c =  "afi_port"
        sdefines +=[
            (('Read-only sensors status information (pointer offset and last sequence number)',)),
            (("X393_AFIMUX0_STATUS",                    c, vrlg.CMPRS_AFIMUX_REG_ADDR0 +             ba, ia, z3, "x393_afimux_status", "ro",          "Status of the AFI MUX 0 (including image pointer)")),
            (("X393_AFIMUX1_STATUS",                    c, vrlg.CMPRS_AFIMUX_REG_ADDR1 +             ba, ia, z3, "x393_afimux_status", "ro",          "Status of the AFI MUX 1 (including image pointer)")),
963
            ]
964 965 966 967 968 969 970 971 972 973 974 975 976 977 978

        #GPIO control
        ba = vrlg.GPIO_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('_',)),
            (('_GPIO contol. Each of the 10 pins can be controlled by the software - individually or simultaneously or from any of the 3 masters (other FPGA modules)',)),
            (('_Currently these modules are;',)),
            (('_     A - camsync (intercamera synchronization), uses up to 4 pins ',)),
            (('_     B - reserved (not yet used) and ',)),
            (('_     C - logger (IMU, GPS, images), uses 6 pins, including separate i2c available on extension boards',)),
            (('_If several enabled ports try to contol the same bit, highest priority has port C, lowest - software controlled',)),
            (("X393_GPIO_SET_PINS",                       "", vrlg.GPIO_SET_PINS +                   ba, 0, None, "x393_gpio_set_pins", "wo",       "State of the GPIO pins and seq. number")),
            (("X393_GPIO_STATUS_CONTROL",                 "", vrlg.GPIO_SET_STATUS +                 ba, 0, None, "x393_status_ctrl", "rw",         "GPIO status control mode"))]
979
        
980 981 982 983 984 985 986 987 988 989 990 991 992 993 994 995 996 997 998 999 1000
        ba = vrlg.STATUS_ADDR
        sdefines +=[
            (('Read-only GPIO pins state',)),
            (("X393_GPIO_STATUS",                         "", vrlg.GPIO_STATUS_REG_ADDR +            ba, 0, None, "x393_gpio_status", "ro",         "State of the GPIO pins and seq. number"))]

        #RTC control
        ba = vrlg.RTC_ADDR
        ia = 0
        c =  ""
        sdefines +=[
            (('RTC control',)),
            (("X393_RTC_USEC",                            "", vrlg.RTC_SET_USEC +                    ba, 0, None, "x393_rtc_usec", "rw",            "RTC microseconds")),
            (("X393_RTC_SEC_SET",                         "", vrlg.RTC_SET_SEC +                     ba, 0, None, "x393_rtc_sec", "rw",             "RTC seconds and set clock")),
            (("X393_RTC_CORR",                            "", vrlg.RTC_SET_CORR +                    ba, 0, None, "x393_rtc_corr", "rw",            "RTC correction (+/- 1/256 full scale)")),
            (("X393_RTC_SET_STATUS",                      "", vrlg.RTC_SET_STATUS +                  ba, 0, None, "x393_status_ctrl", "rw",         "RTC status control mode, write makes a snapshot to be read out"))]
        ba = vrlg.STATUS_ADDR
        sdefines +=[
            (('Read-only RTC state',)),
            (("X393_RTC_STATUS",                         "", vrlg.RTC_STATUS_REG_ADDR +              ba, 0, None, "x393_rtc_status", "ro",          "RTC status reg")),
            (("X393_RTC_STATUS_SEC",                     "", vrlg.RTC_SEC_USEC_ADDR + 0 +            ba, 0, None, "x393_rtc_sec", "ro",             "RTC snapshot seconds")),
            (("X393_RTC_STATUS_USEC",                    "", vrlg.RTC_SEC_USEC_ADDR + 1 +            ba, 0, None, "x393_rtc_usec", "ro",            "RTC snapshot microseconds"))]
1001
        
1002 1003 1004 1005 1006 1007 1008 1009 1010 1011 1012 1013 1014 1015 1016 1017 1018
        #CAMSYNC control
        ba = vrlg.CAMSYNC_ADDR
        ia = 0
        c =  "sens_chn"
        sdefines +=[
            (('CAMSYNC control',)),
            (("X393_CAMSYNC_MODE",                        "", vrlg.CAMSYNC_MODE +                    ba, 0, None, "x393_camsync_mode", "wo",        "CAMSYNC mode")),
            (("X393_CAMSYNC_TRIG_SRC",                    "", vrlg.CAMSYNC_TRIG_SRC +                ba, 0, None, "x393_camsync_io", "wo",          "CAMSYNC trigger source")),
            (("X393_CAMSYNC_TRIG_DST",                    "", vrlg.CAMSYNC_TRIG_DST +                ba, 0, None, "x393_camsync_io", "wo",          "CAMSYNC trigger destination")),
            (('_Trigger period has special value for small (<255) values written to this register',)),
            (('_    d == 0 - disable (stop periodic mode)',)),
            (('_    d == 1 - single trigger',)),
            (('_    d == 2..255 - set output pulse / input-output serial bit duration (no start generated)',)),
            (('_    d >= 256 - repetitive trigger',)),
            (("X393_CAMSYNC_TRIG_PERIOD",                 "", vrlg.CAMSYNC_TRIG_PERIOD +             ba, 0, None, "u32*", "rw",                     "CAMSYNC trigger period")),
            (("X393_CAMSYNC_TRIG_DELAY",                  c,  vrlg.CAMSYNC_TRIG_DELAY0 +             ba, 1, z3,   "u32*", "rw",                     "CAMSYNC trigger delay"))]
        
1019 1020 1021 1022 1023 1024 1025 1026 1027 1028 1029 1030 1031 1032 1033 1034 1035 1036 1037 1038
        ba = vrlg.CMDFRAMESEQ_ADDR_BASE
        ia = vrlg.CMDFRAMESEQ_ADDR_INC
        c =  "sens_chn"
        sdefines +=[
            (('Command sequencer control',)),
            (('_Controller is programmed through 32 locations. Each registers but the control require two writes:',)),
            (('_First write - register address (AXI_WR_ADDR_BITS bits), second - register data (32 bits)',)),
            (('_Writing to the contol register (0x1f) resets the first/second counter so the next write will be "first"',)),
            (('_0x0..0xf write directly to the frame number [3:0] modulo 16, except if you write to the frame',)),
            (('_          "just missed" - in that case data will go to the current frame.',)),
            (('_ 0x10 - write seq commands to be sent ASAP',)),
            (('_ 0x11 - write seq commands to be sent after the next frame starts',)), 
            (('_',)),
            (('_ 0x1e - write seq commands to be sent after the next 14 frame start pulses',)),
            (('_ 0x1f - control register:',)),
            (('_     [14] -   reset all FIFO (takes 32 clock pulses), also - stops seq until run command',)),
            (('_     [13:12] - 3 - run seq, 2 - stop seq , 1,0 - no change to run state',)),
            (('_       [1:0] - 0: NOP, 1: clear IRQ, 2 - Clear IE, 3: set IE',)),
            (("X393_CMDFRAMESEQ_CTRL",                    c,  vrlg.CMDFRAMESEQ_CTRL +                ba, ia, z3, "x393_cmdframeseq_mode", "wo",     "CMDFRAMESEQ control register")),
            (("X393_CMDFRAMESEQ_ABS",          (c,"offset"),  vrlg.CMDFRAMESEQ_ABS +                 ba, (ia,1), (z3,z15), "u32*", "wo",            "CMDFRAMESEQ absolute frame address/command")),
1039 1040 1041 1042 1043 1044
            (("X393_CMDFRAMESEQ_REL",          (c,"offset"),  vrlg.CMDFRAMESEQ_REL +                 ba, (ia,1), (z3,z14), "u32*", "wo",            "CMDFRAMESEQ relative frame address/command"))]
        
        ba = 0
        ia = 0
        c =  ""
        sdefines +=[
1045
            (('_Command sequencer multiplexer, provides current frame number for each sensor channel and interrupt status/interrupt masks for them.',)),
1046 1047 1048
            (('_Interrupts and interrupt masks are controlled through channel CMDFRAMESEQ module',)),
            (("X393_CMDSEQMUX_STATUS_CTRL",               "",  vrlg.CMDSEQMUX_ADDR,                      0, None, "x393_status_ctrl", "rw",           "CMDSEQMUX status control mode (status provides current frame numbers)")),
            (("X393_CMDSEQMUX_STATUS",                    "",  vrlg.STATUS_ADDR + vrlg.CMDSEQMUX_STATUS, 0, None, "x393_cmdseqmux_status", "ro",      "CMDSEQMUX status data (frame numbers and interrupts"))]
1049 1050 1051 1052 1053 1054 1055 1056 1057 1058 1059 1060 1061 1062 1063 1064 1065 1066 1067 1068 1069 1070 1071 1072 1073 1074 1075 1076 1077 1078 1079 1080

        sdefines +=[
            (('Event logger',)),
            (('_Event logger configuration/data is writtent to the module ising two 32-bit register locations : data and address.',)),
            (('_Address consists of 2 parts - 2-bit page (configuration, imu, gps, message) and a 5-bit sub-address autoincremented when writing data.',)),
            (('_Register pages:',)),
            (("X393_LOGGER_PAGE_CONF",                    "", 0 ,                                0, None, None, "",    "Logger configuration page")),
            (("X393_LOGGER_PAGE_IMU",                     "", vrlg.LOGGER_PAGE_IMU ,             0, None, None, "",    "Logger IMU parameters page")),
            (("X393_LOGGER_PAGE_GPS",                     "", vrlg.LOGGER_PAGE_GPS ,             0, None, None, "",    "Logger GPS parameters page")),
            (("X393_LOGGER_PAGE_MSG",                     "", vrlg.LOGGER_PAGE_MSG ,             0, None, None, "",    "Logger MSG (odometer) parameters page")),
            (('_Register configuration addresses (with X393_LOGGER_PAGE_CONF):',)),
            (("X393_LOGGER_PERIOD",                       "", vrlg.LOGGER_PERIOD ,               0, None, None, "",    "IMU period (in SPI clocks, high word 0xffff - use IMU ready)")),
            (("X393_LOGGER_BIT_DURATION",                 "", vrlg.LOGGER_BIT_DURATION ,         0, None, None, "",    "IMU SPI bit duration (in mclk == 50 ns periods?)")),
            (("X393_LOGGER_BIT_HALF_PERIOD",              "", vrlg.LOGGER_BIT_HALF_PERIOD,       0, None, None, "",    "Logger rs232 half bit period (in mclk == 50 ns periods?)")),
            (("X393_LOGGER_CONFIG",                       "", vrlg.LOGGER_CONFIG ,               0, None, None, "",    "Logger IMU parameters page")),
            
            (("X393_LOGGER_STATUS_CTRL",                  "",  vrlg.LOGGER_STATUS,                       0, None,       "x393_status_ctrl", "rw",     "Logger status configuration (to report sample number)")),
            (("X393_LOGGER_DATA",                         "",  vrlg.LOGGER_ADDR + 0,                     0, None,       "x393_logger_data", "wo",     "Logger register write data")),
            (("X393_LOGGER_ADDRESS",                      "",  vrlg.LOGGER_ADDR + 1,                     0, None,       "x393_logger_address", "wo",  "Logger register write page/address")),
            (("X393_LOGGER_STATUS",                       "",  vrlg.STATUS_ADDR + vrlg.LOGGER_STATUS_REG_ADDR, 0, None, "x393_logger_status", "ro",   "Logger status data (sequence number)"))]
#TODO: Add interrupt for the logger?

        #MULT SAXI DMA engine control
        ba = 0
        ia = 0
        c =  "chn"
        sdefines +=[
            (('MULT SAXI DMA engine control. Of 4 channels only one (number 0) is currently used - for the event logger',)),
            (("X393_MULT_SAXI_STATUS_CTRL",         "",  vrlg.MULT_SAXI_CNTRL_ADDR,                      0, None, "x393_status_ctrl", "rw",           "MULT_SAXI status control mode (status provides current DWORD pointer)")),
            (("X393_MULT_SAXI_BUF_ADDRESS",         c,   vrlg.MULT_SAXI_ADDR + 0,                        2, z3,   "x393_mult_saxi_al", "wo",          "MULT_SAXI buffer start address in DWORDS")),
            (("X393_MULT_SAXI_BUF_LEN",             c,   vrlg.MULT_SAXI_ADDR + 1,                        2, z3,   "x393_mult_saxi_al", "wo",          "MULT_SAXI buffer length in DWORDS")),
            (("X393_MULT_SAXI_STATUS",              c,   vrlg.STATUS_ADDR + vrlg.MULT_SAXI_STATUS_REG,   1, z3,   "x393_mult_saxi_al", "ro",          "MULT_SAXI current DWORD pointer"))]
1081 1082 1083 1084 1085 1086 1087 1088 1089 1090 1091 1092 1093 1094 1095 1096 1097 1098 1099 1100 1101 1102 1103 1104 1105 1106 1107 1108 1109 1110

        #MULTI_CLK global clock generation PLLs
        ba = 0
        ia = 0
        c =  "chn"
        sdefines +=[
            (('MULTI_CLK - global clock generation PLLs. Interface provided for debugging, no interaction is needed for normal operation',)),
            (("X393_MULTICLK_STATUS_CTRL",          "",  vrlg.CLK_ADDR + vrlg.CLK_STATUS,                0, None, "x393_status_ctrl", "rw",           "MULTI_CLK status generation (do not use or do not set auto)")),
            (("X393_MULTICLK_CTRL",                 "",  vrlg.CLK_ADDR + vrlg.CLK_CNTRL,                 0, None, "x393_multiclk_ctl", "rw",          "MULTI_CLK reset and power down control")),
            (("X393_MULTICLK_STATUS",               "",  vrlg.STATUS_ADDR + vrlg.CLK_STATUS_REG_ADDR,    0, None, "x393_multiclk_status", "ro",       "MULTI_CLK lock and toggle state"))]

        #DEBUG ring module
        ba = 0
        ia = 0
        c =  "chn"
        sdefines +=[
            (('Debug ring module',)),
            (('_Debug ring module (when enabled with DEBUG_RING in system_defines.vh) provides low-overhead read/write access to internal test points',)),
            (('_To write data you need to write 32-bit data with x393_debug_shift(u32) multiple times to fill the ring register (length depends on',)),
            (('_implementation), skip this step if only reading from the modules under test is required.',)),
            (('_Exchange data with x393_debug_load(), the data from the ring shift register.',)),
            (('_Write 0xffffffff (or other "magic" data) if the ring length is unknown - this DWORD will appear on the output after the useful data',)),
            (('_Read all data, waiting for status sequence number to be incremented,status mode should be set to auto (3) wor each DWORD certain',)),
            (('_number of times or until the "magic" DWORD appears, writing "magic" to shift out next 32 bits.',)),
            (("X393_DEBUG_STATUS_CTRL",             "",  vrlg.DEBUG_ADDR + vrlg.DEBUG_SET_STATUS,        0, None, "x393_status_ctrl", "rw",           "Debug ring status generation - set to auto(3) if used")),
            (("X393_DEBUG_LOAD",                    "",  vrlg.DEBUG_ADDR + vrlg.DEBUG_LOAD,              0, None, "", "",                             "Debug ring copy shift register to/from tested modules")),
            (("X393_DEBUG_SHIFT",                   "",  vrlg.DEBUG_ADDR + vrlg.DEBUG_SHIFT_DATA,        0, None, "u32*", "wo",                       "Debug ring shift ring by 32 bits")),
            (("X393_DEBUG_STATUS",                  "",  vrlg.STATUS_ADDR + vrlg.DEBUG_STATUS_REG_ADDR,  0, None, "x393_debug_status", "ro",          "Debug read status (watch sequence number)")),
            (("X393_DEBUG_READ",                    "",  vrlg.STATUS_ADDR + vrlg.DEBUG_READ_REG_ADDR,    0, None, "u32*", "ro",                       "Debug read DWORD form ring register"))]

1111 1112 1113 1114 1115 1116 1117 1118
        return sdefines
    
    def define_other_macros(self): # Used mostly for development/testing, not needed for normal camera operation
        ba = vrlg.MCNTRL_SCANLINE_CHN3_ADDR
        c =  ""
        sdefines = []
        sdefines +=[
            (('Write-only addresses to program memory channel 3 (test channel)',)),
1119
            (("X393_MCNTRL_CHN3_SCANLINE_MODE",            c, vrlg.MCNTRL_SCANLINE_MODE +             ba, 0, None, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
1120
            (("X393_MCNTRL_CHN3_SCANLINE_STATUS_CNTRL",    c, vrlg.MCNTRL_SCANLINE_STATUS_CNTRL +     ba, 0, None, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
1121 1122 1123 1124 1125 1126 1127
            (("X393_MCNTRL_CHN3_SCANLINE_STARTADDR",       c, vrlg.MCNTRL_SCANLINE_STARTADDR +        ba, 0, None, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_MCNTRL_CHN3_SCANLINE_FRAME_SIZE",      c, vrlg.MCNTRL_SCANLINE_FRAME_SIZE +       ba, 0, None, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_MCNTRL_CHN3_SCANLINE_FRAME_LAST",      c, vrlg.MCNTRL_SCANLINE_FRAME_LAST +       ba, 0, None, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_MCNTRL_CHN3_SCANLINE_FRAME_FULL_WIDTH",c, vrlg.MCNTRL_SCANLINE_FRAME_FULL_WIDTH + ba, 0, None, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_MCNTRL_CHN3_SCANLINE_WINDOW_WH",       c, vrlg.MCNTRL_SCANLINE_WINDOW_WH +        ba, 0, None, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_MCNTRL_CHN3_SCANLINE_WINDOW_X0Y0",     c, vrlg.MCNTRL_SCANLINE_WINDOW_X0Y0 +      ba, 0, None, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_MCNTRL_CHN3_SCANLINE_STARTXY",         c, vrlg.MCNTRL_SCANLINE_WINDOW_STARTXY +   ba, 0, None, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register"))]
1128 1129 1130 1131
        ba = vrlg.MCNTRL_TILED_CHN2_ADDR
        c =  ""
        sdefines +=[
            (('Write-only addresses to program memory channel 2 (test channel)',)),
1132
            (("X393_MCNTRL_CHN2_TILED_MODE",               c, vrlg.MCNTRL_TILED_MODE +                ba, 0, None, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
1133
            (("X393_MCNTRL_CHN2_TILED_STATUS_CNTRL",       c, vrlg.MCNTRL_TILED_STATUS_CNTRL +        ba, 0, None, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
1134 1135 1136 1137 1138 1139 1140 1141
            (("X393_MCNTRL_CHN2_TILED_STARTADDR",          c, vrlg.MCNTRL_TILED_STARTADDR +           ba, 0, None, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_MCNTRL_CHN2_TILED_FRAME_SIZE",         c, vrlg.MCNTRL_TILED_FRAME_SIZE +          ba, 0, None, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_MCNTRL_CHN2_TILED_FRAME_LAST",         c, vrlg.MCNTRL_TILED_FRAME_LAST +          ba, 0, None, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_MCNTRL_CHN2_TILED_FRAME_FULL_WIDTH",   c, vrlg.MCNTRL_TILED_FRAME_FULL_WIDTH +    ba, 0, None, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_MCNTRL_CHN2_TILED_WINDOW_WH",          c, vrlg.MCNTRL_TILED_WINDOW_WH +           ba, 0, None, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_MCNTRL_CHN2_TILED_WINDOW_X0Y0",        c, vrlg.MCNTRL_TILED_WINDOW_X0Y0 +         ba, 0, None, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_MCNTRL_CHN2_TILED_STARTXY",            c, vrlg.MCNTRL_TILED_WINDOW_STARTXY +      ba, 0, None, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register")),
            (("X393_MCNTRL_CHN2_TILED_TILE_WHS",           c, vrlg.MCNTRL_TILED_TILE_WHS +            ba, 0, None, "x393_mcntrl_window_tile_whs", "wo",       "Set tile size/step (tiled mode only)"))]
1142 1143 1144 1145
        ba = vrlg.MCNTRL_TILED_CHN4_ADDR
        c =  ""
        sdefines +=[
            (('Write-only addresses to program memory channel 4 (test channel)',)),
1146
            (("X393_MCNTRL_CHN4_TILED_MODE",               c, vrlg.MCNTRL_TILED_MODE +                ba, 0, None, "x393_mcntrl_mode_scan", "wo",             "Set mode register (write last after other channel registers are set)")),
1147
            (("X393_MCNTRL_CHN4_TILED_STATUS_CNTRL",       c, vrlg.MCNTRL_TILED_STATUS_CNTRL +        ba, 0, None, "x393_status_ctrl", "rw",                  "Set status control register (status update mode)")),
1148 1149 1150 1151 1152 1153 1154 1155
            (("X393_MCNTRL_CHN4_TILED_STARTADDR",          c, vrlg.MCNTRL_TILED_STARTADDR +           ba, 0, None, "x393_mcntrl_window_frame_sa", "wo",       "Set frame start address")),
            (("X393_MCNTRL_CHN4_TILED_FRAME_SIZE",         c, vrlg.MCNTRL_TILED_FRAME_SIZE +          ba, 0, None, "x393_mcntrl_window_frame_sa_inc", "wo",   "Set frame size (address increment)")),
            (("X393_MCNTRL_CHN4_TILED_FRAME_LAST",         c, vrlg.MCNTRL_TILED_FRAME_LAST +          ba, 0, None, "x393_mcntrl_window_last_frame_num", "wo", "Set last frame number (number of frames in buffer minus 1)")),
            (("X393_MCNTRL_CHN4_TILED_FRAME_FULL_WIDTH",   c, vrlg.MCNTRL_TILED_FRAME_FULL_WIDTH +    ba, 0, None, "x393_mcntrl_window_full_width", "wo",     "Set frame full(padded) width")),
            (("X393_MCNTRL_CHN4_TILED_WINDOW_WH",          c, vrlg.MCNTRL_TILED_WINDOW_WH +           ba, 0, None, "x393_mcntrl_window_width_height", "wo",   "Set frame window size")),
            (("X393_MCNTRL_CHN4_TILED_WINDOW_X0Y0",        c, vrlg.MCNTRL_TILED_WINDOW_X0Y0 +         ba, 0, None, "x393_mcntrl_window_left_top", "wo",       "Set frame position")),
            (("X393_MCNTRL_CHN4_TILED_STARTXY",            c, vrlg.MCNTRL_TILED_WINDOW_STARTXY +      ba, 0, None, "x393_mcntrl_window_startx_starty", "wo",  "Set startXY register")),
            (("X393_MCNTRL_CHN4_TILED_TILE_WHS",           c, vrlg.MCNTRL_TILED_TILE_WHS +            ba, 0, None, "x393_mcntrl_window_tile_whs", "wo",       "Set tile size/step (tiled mode only)"))]
1156 1157
        return sdefines
    
1158 1159
    def expand_define_maxi0(self, define_tuple, mode, frmt_spcs = None):
        if len(define_tuple)  == 1 :
1160
            return self.expand_define(define_tuple = define_tuple, frmt_spcs = frmt_spcs)
1161 1162 1163 1164 1165 1166 1167 1168 1169 1170 1171 1172 1173 1174 1175 1176
        elif len(define_tuple)  == 8:
            name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
            if data_type is None:  #just constants, no offset and multiplication
                if (mode == 'defines') or (mode =='func_decl') :
                    return self.expand_define(define_tuple = (name,
                                                              var_name,
                                                              address,
                                                              address_inc,
                                                              var_range,
                                                              data_type,
                                                              rw,
                                                              comment),
                                              frmt_spcs = frmt_spcs)
                else:
                    return ""
            else:
1177 1178 1179 1180 1181
                if isinstance(address_inc,(list,tuple)): # var_name, var_range are also lists/tuples of the same length
                    address_inc = [4 * d for d in address_inc]
                else:
                    address_inc = 4 * address_inc

1182 1183 1184 1185
                if (mode == 'defines') :
                    return self.expand_define(define_tuple = (name,
                                                              var_name,
                                                              address * 4 + self.MAXI0_BASE,
1186
                                                              address_inc, # * 4,
1187 1188 1189 1190 1191 1192 1193 1194 1195
                                                              var_range,
                                                              data_type,
                                                              rw,
                                                              comment),
                                              frmt_spcs = frmt_spcs)
                elif (mode =='func_decl'):
                    return self.func_declare (define_tuple = (name,
                                                              var_name,
                                                              address * 4 + self.MAXI0_BASE,
1196
                                                              address_inc, # * 4,
1197 1198 1199 1200 1201 1202 1203 1204
                                                              var_range,
                                                              data_type,
                                                              rw,
                                                              comment),
                                              frmt_spcs = frmt_spcs)
                elif (mode =='func_def'):
                    return self.func_define  (define_tuple = (name,
                                                              var_name,
1205
                                                              address * 4, #  + self.MAXI0_BASE,
1206
                                                              address_inc, # * 4,
1207 1208 1209 1210 1211 1212 1213 1214 1215 1216 1217 1218 1219 1220 1221 1222 1223 1224 1225 1226 1227 1228 1229 1230 1231 1232 1233 1234 1235 1236 1237 1238 1239 1240 1241 1242 1243 1244 1245 1246 1247 1248 1249 1250 1251 1252 1253 1254
                                                              var_range,
                                                              data_type,
                                                              rw,
                                                              comment),
                                              frmt_spcs = frmt_spcs)
                else:
                    print ("Unknown mode:", mode)    
                        
        else:
            print ("****** wrong tuple length: ",define_tuple)

    def  func_declare(self,
                      define_tuple,
                      frmt_spcs):
        frmt_spcs=self.fix_frmt_spcs(frmt_spcs)
        
#        name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
        rw= define_tuple[6]
        s=""
        if 'w' in rw:
            s += self.func_set(isDefine=False,define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        if 'r' in rw:
            if s:
                s += '\n'
            s += self.func_get(isDefine=False, define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        if (not 'r' in rw) and (not 'w' in rw):     
            s += self.func_touch(isDefine=False,define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        return s    

    def func_define(self,
                      define_tuple,
                      frmt_spcs):
        frmt_spcs=self.fix_frmt_spcs(frmt_spcs)
#        name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
        rw= define_tuple[6]
        s=""
        if 'w' in rw:
            s += self.func_set(isDefine=True, define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        if 'r' in rw:
            if s:
                s += '\n'
            s += self.func_get(isDefine=True, define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        if (not 'r' in rw) and (not 'w' in rw):     
            s += self.func_touch(isDefine=True, define_tuple=define_tuple, frmt_spcs = frmt_spcs)
        return s    
    def str_tab_stop(self,s,l):
        if len(s)>= l:
            return s
1255
        else:
1256 1257 1258 1259 1260 1261 1262 1263
            return s + (" "*(l - len(s)))  
    
    def func_get(self,
                  isDefine,
                  define_tuple,
                  frmt_spcs):
#        name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
        name, var_name, address, address_inc, _, data_type, rw, comment = define_tuple
1264 1265
        multivar = isinstance(address_inc,(list,tuple)) # var_name, var_range are also lists/tuples of the same length
        
1266 1267 1268 1269 1270 1271 1272 1273 1274 1275
        stops=frmt_spcs[('declare','define')[isDefine]]
        #TODO: add optional argument range check?
        data_type = self.fix_data_type(data_type)
        sz=self.typedefs[data_type]['size'] # check it exists
        if (sz > 32):
            print ("***** Only 32-bit data is supported, %s used for %s is %d bit"%(data_type, name, sz))
        fname = name.lower()
        if ('r' in rw) and ('w' in rw):
            fname = 'get_'+fname
            comment = "" # set is supposed to go first, if both - only set has comment
1276 1277 1278 1279 1280 1281 1282 1283 1284
        if multivar:
            args = "int %s"%(var_name[0].lower())
            for vn in var_name[1:]:
                args += ", int %s"%(vn.lower())
        else:       
            arg = var_name.lower()   
            args = 'void'
            if arg and address_inc:
                args = 'int '+ arg    
1285 1286 1287 1288 1289 1290 1291
        s = "%s "%(data_type)
        s = self.str_tab_stop(s,stops[0])
        s += "%s"%(fname)
        s = self.str_tab_stop(s,stops[1])
        s += "(%s)"%(args)
        s = self.str_tab_stop(s,stops[2])
        if isDefine:
1292 1293 1294 1295 1296
            if self.typedefs[data_type]['code']: # not just u32
                td = 'd.%s'%(frmt_spcs['data32'])
            else:
                td='d'
                
1297
            s+='{ %s d; %s = readl(mmio_ptr + '%(data_type, td)
1298
            if address_inc:
1299
                s+='(0x%04x'%(address)
1300 1301 1302 1303
                if multivar:
                    for vn, vi in zip (var_name, address_inc):
                        s+=' + 0x%x * %s'%(vi, vn.lower())
                else:
1304 1305
                    s+=' + 0x%x * %s'%(address_inc, arg)
                s += ')'
1306
            else:
1307
                s+='0x%04x'%(address)
1308
            s+='); return d; }'
1309 1310 1311 1312 1313 1314 1315 1316 1317 1318 1319 1320 1321
        else:
            s += ';'
        if comment:
            s = self.str_tab_stop(s,stops[3])
            s += ' // %s'%(comment) 
        return s

    def  func_set(self,
                  isDefine,
                  define_tuple,
                  frmt_spcs):
#        name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
        name, var_name, address, address_inc, _, data_type, rw, comment = define_tuple
1322
        multivar = isinstance(address_inc,(list,tuple)) # var_name, var_range are also lists/tuples of the same length
1323 1324 1325
        stops=frmt_spcs[('declare','define')[isDefine]]
        #TODO: add optional argument range check?
        data_type = self.fix_data_type(data_type)
1326
        #        self.typedefs['u32']= {'comment':'unsigned 32-bit', 'code':'', 'size':32, 'type':''}
1327 1328 1329 1330 1331 1332 1333
        sz=self.typedefs[data_type]['size'] # check it exists
        if (sz > 32):
            print ("***** Only 32-bit data is supported, %s used for %s is %d bit"%(data_type, name, sz))
        fname = name.lower()
        if ('r' in rw) and ('w' in rw):
            fname = 'set_'+fname
        args = '%s d'%(data_type)
1334 1335 1336 1337 1338 1339 1340
        if multivar:
            for vn in var_name:
                args += ', int '+ vn.lower()
        else:
            arg = var_name.lower()   
            if arg and address_inc:
                args += ', int '+ arg    
1341 1342 1343 1344 1345 1346 1347
        s = "void "
        s = self.str_tab_stop(s,stops[0])
        s += "%s"%(fname)
        s = self.str_tab_stop(s,stops[1])
        s += "(%s)"%(args)
        s = self.str_tab_stop(s,stops[2])
        if isDefine:
1348 1349 1350 1351
            if self.typedefs[data_type]['code']: # not just u32
                td = 'd.%s'%(frmt_spcs['data32'])
            else:
                td='d'
1352
            s+='{writel(%s, mmio_ptr + '%(td)
1353
            if address_inc:
1354
                s+='(0x%04x'%(address)
1355 1356 1357 1358
                if multivar:
                    for vn, vi in zip (var_name, address_inc):
                        s+=' + 0x%x * %s'%(vi, vn.lower())
                else:
1359 1360
                    s+=' + 0x%x * %s'%(address_inc, arg)
                s += ')'
1361
            else:
1362
                s+='0x%04x'%(address)
1363
            s+=');}'
1364 1365 1366 1367 1368 1369 1370 1371 1372 1373 1374 1375 1376
        else:
            s += ';'
        if comment:
            s = self.str_tab_stop(s,stops[3])
            s += ' // %s'%(comment) 
        return s

    def  func_touch(self,
                  isDefine,
                  define_tuple,
                  frmt_spcs):
#       name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
        name, var_name, address, address_inc, _,            _,       _,  comment = define_tuple
1377
        multivar = isinstance(address_inc,(list,tuple)) # var_name, var_range are also lists/tuples of the same length
1378 1379 1380
        stops=frmt_spcs[('declare','define')[isDefine]]
        #TODO: add optional argument range check?
        fname = name.lower()
1381 1382 1383 1384 1385 1386 1387 1388 1389
        if multivar:
            args = "int %s"%(var_name[0].lower())
            for vn in var_name[1:]:
                args += ", int %s"%(vn.lower())
        else:       
            arg = var_name.lower()   
            args = 'void'
            if arg and address_inc:
                args = 'int '+ arg    
1390 1391 1392 1393 1394 1395 1396
        s = "void "
        s = self.str_tab_stop(s,stops[0])
        s += "%s"%(fname)
        s = self.str_tab_stop(s,stops[1])
        s += "(%s)"%(args)
        s = self.str_tab_stop(s,stops[2])
        if isDefine:
1397
#            s+='{'
1398
            s+='{writel(0, mmio_ptr + '
1399
            if address_inc:
1400
                s+='(0x%04x'%(address)
1401 1402 1403 1404
                if multivar:
                    for vn, vi in zip (var_name, address_inc):
                        s+=' + 0x%x * %s'%(vi, vn.lower())
                else:
1405 1406
                    s+=' + 0x%x * %s'%(address_inc, arg)
                s += ')'
1407
            else:
1408
                s+='0x%04x'%(address)
1409
            s+=');}'
1410 1411 1412 1413 1414 1415 1416 1417 1418 1419 1420 1421 1422 1423
        else:
            s += ';'
        if comment:
            s = self.str_tab_stop(s,stops[3])
            s += ' // %s'%(comment) 
        return s

    def fix_data_type(self,data_type):
        if data_type:
            if data_type[-1] == "*": # skip adding '_t": some_type -> some_type_t, u32* -> u32
                data_type=data_type[0:-1]
            else:    
                data_type = data_type +"_t"
        return data_type
1424 1425 1426 1427 1428 1429 1430
            
    def expand_define(self, define_tuple, frmt_spcs = None):
        frmt_spcs=self.fix_frmt_spcs(frmt_spcs)
        s=""
        if len(define_tuple)  ==1 :
            comment = define_tuple[0]
            if comment:
1431 1432 1433 1434
                if comment[0] == "_":
                    s += "// %s"%(comment[1:]) # for multi-line comments
                else:
                    s += "\n// %s\n"%(comment)
1435
        else:
1436
            name, var_name, address, address_inc, var_range, data_type, rw, comment = define_tuple
1437
            multivar = isinstance(address_inc,(list,tuple)) # var_name, var_range are also lists/tuples of the same length