Beispiel #1
0
def write(can, computers, output_path=bus_path):
    header_name = '_CAN_LIBRARY_BUS_H'

    with open(output_path, 'w') as f:
        fw = f.write

        fw(ifndef(header_name))

        # Create enum among buses
        fw('typedef enum {\n')
        for bus in can.bus:
            fw('\t' + bus.name + ',\n')
        fw('} CANlib_Bus_T;\n\n')

        raw_buses = set()
        for computer in computers:
            if not ('can' in computer.participation['name'].keys()):
                # This computer neither sends nor recieves can messages
                continue

            raw_buses |= set(
                computer.participation['name']['can'].mapping.values())

        assert 'INVALID_BUS' not in raw_buses, "INVALID_BUS is a reserved bus name"

        fw('typedef enum {\n')
        for bus in raw_buses:
            fw('\t' + bus + ',\n')
        fw('\tINVALID_BUS\n} CAN_Raw_Bus_T;\n\n')

        # Create forms enum for each bus
        for bus in can.bus:
            fw('typedef enum {\n')

            # First frame needs to start at 2, the rest will follow
            first_frame = True
            for msg in bus.frame:
                if is_multplxd(msg):
                    for frame in msg.frame:
                        fw('\t' + coord(bus.name, msg.name, frame.name))
                        if first_frame:
                            fw(' = 2')
                        first_frame = False
                        fw(',\n')
                else:
                    fw('\t' + coord(bus.name, msg.name))
                    if first_frame:
                        fw(' = 2')
                    first_frame = False
                    fw(',\n')

            fw('} ' + '{}_T;\n\n'.format(coord(bus.name)))

            fw('{}_T CANlib_Identify_{}(Frame* frame);'.format(
                coord(bus.name), coord(bus.name, prefix=False)) + '\n\n')

        fw(endif(header_name))
Beispiel #2
0
def msg_handler(frame, name_prepends, fw):
    fw('typedef struct {\n')

    for atom in frame.atom:
        if atom.type.isenum():
            enum_name = coord(name_prepends, frame.name, atom.name) + '_T'
            fw('\t{} {};\n'.format(enum_name, atom.name))
        else:
            fw('\t{} {};\n'.format(atom.type.ctype(), atom.name))

    fw('} ' + '{}_T;\n\n'.format(coord(name_prepends, frame.name)))
Beispiel #3
0
def single_handler(frame, name_prepends, num_tabs, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw(
        '\t' * num_tabs + 'case CANlib_{}_key:'.format(tot_name) + '\n' +
        '\t' * (num_tabs + 1) + 'CANlib_Handle_{}(&frame);\n'.format(tot_name) +
        '\t' * (num_tabs + 1) + 'break;\n'
    )
def write_declare(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('CANlib_Transmit_Error_T CANlib_Transmit_{}'.format(tot_name) +
       '(CANlib_{}_T *type);\n'.format(tot_name))
    fw('void CANlib_Pack_{}(CANlib_{}_T *type_in, Frame *can_out);\n'.format(
        tot_name, tot_name) +
       'void CANlib_Unpack_{}(Frame *can_in, CANlib_{}_T *type_out);\n'.format(
           tot_name, tot_name))
def define_pub_frame(frame, name_prepends, busnm, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('void CANlib_Send_{}(CANlib_{}_T *inp)'.format(tot_name, tot_name) +
       ' {\n')

    if frame.period is not None:
        fw('\tLIMIT(CANlib_{});\n'.format(tot_name))

    fw('\tFrame frame;\n' + '\tCANlib_Pack_' + tot_name + '(inp, &frame);\n' +
       '\tCANlib_TransmitFrame(&frame, ' + busnm + ');\n'
       '}\n\n')
Beispiel #6
0
def write_can_pack(frame, name_prepends, bus_ext, fw, parent_slice=None):
    is_multplxd_subframe = parent_slice is not None

    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('void CANlib_Pack_' + tot_name + '(CANlib_' + tot_name +
       '_T *type_in, Frame *can_out)'
       '{\n\t'
       'uint64_t bitstring = 0;'
       '\n')

    if is_multplxd_subframe:
        if True:  # TODO: check endianness, like atom.type.endianness == Endianness.LITTLE:
            # TODO: Actually grab key type
            fw('\t'
               'bitstring = INSERT(CANlib_' + tot_name + '_key, bitstring, ' +
               str(parent_slice.start) + ', ' + str(parent_slice.length) + ');'
               '\n\n')

    write_atoms_pack(fw, frame.atom)

    length = max(atom.slice.start + atom.slice.length for atom in frame.atom)

    fw('\t' 'from_bitstring(&bitstring, can_out->data);' '\n')

    key_name = ""
    if not is_multplxd_subframe:
        key_name = coord(name_prepends, frame.name, 'key')
    else:
        key_name = coord(name_prepends, 'key')

    fw('\t'
       'can_out->id = {};'.format(key_name) + '\n'
       '\t'
       'can_out->dlc = ' + str(ceil(length / 8)) + ';'
       '\n'
       '\t'
       'can_out->extended = ' + str(bus_ext).lower() + ';'
       '\n'
       '}'
       '\n\n')
Beispiel #7
0
def write_can_unpack(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('void CANlib_Unpack_' + tot_name + '(Frame *can_in, CANlib_' +
       tot_name + '_T *type_out) {\n'
       '\t'
       'uint64_t bitstring = 0;'
       '\n'
       '\t'
       'to_bitstring(can_in->data, &bitstring);\n')

    write_atoms_unpack(fw, frame.atom, tot_name)

    fw('}' '\n\n')
Beispiel #8
0
 def msg_handler(frame, name_prepends):
     attr = None
     try:
         attr = getattr(frame, attrnm)
     except AttributeError as e:
         if not attrnm in optional_props:
             raise e
     if attr is None:
         if attrnm in optional_props:
             return
         else:
             raise AttributeError('{} missing required attribute {}'.format(frame.name, attrnm))
     attr = transform(attr)
     fw(templ[form].format(coord(name_prepends, frame.name, finalnm), attr))
Beispiel #9
0
def multplxd_handler(frame, name_prepends, num_tabs, fw):
    fw('\t' * num_tabs + 'case {}_key:\n'.format(coord(name_prepends, frame.name)))
    key_size = ceil(frame.slice.length / 8) * 8
    key_name = '_'.join([name_prepends,frame.name, 'key'])
    fw('\t' * (num_tabs + 1) + 'to_bitstring(frame.data, &bitstring);' '\n')
    fw(
        '\t' * (num_tabs + 1) + 'uint{}_t {} = EXTRACT(bitstring, {}, {});\n'.format(key_size, key_name, frame.slice.start, frame.slice.length) + '\t' * (num_tabs + 1) + 'switch(' + key_name + ') {' '\n'
    )

    name_prepends += '_' + frame.name

    for sub_frame in frame.frame:
        if is_multplxd(sub_frame):
            multplxd_handler(sub_frame, name_prepends, num_tabs + 2, fw)
        else:
            single_handler(sub_frame, name_prepends, num_tabs + 2, fw)
    fw('\t' * (num_tabs + 1) + '}\n')
Beispiel #10
0
def handle_frame(frame, name_prepends, fw):
    for atom in frame.atom:
        tot_name = coord(name_prepends, frame.name, atom.name)
        if atom.type.isenum():
            # Only C++11 feature
            # fw('typedef enum ' + (atom.type.type + ' ' if atom.type.type else '') + '{\n')

            fw('typedef enum {\n')

            for enum in atom.type.enum:
                assert enum.name != 'NUM_FIELDS'
                fw(templ['enum'].format(tot_name + '_' + enum.name,
                                        enum.value))

            fw('\t' + tot_name + '_' + 'NUM_FIELDS\n')

            fw('} ' + '{}_T;\n\n'.format(tot_name))
Beispiel #11
0
def write_atoms_unpack(fw, atoms, tot_name):
    for atom in atoms:
        if atom.type.isenum():
            enum_name = coord(tot_name, atom.name) + '_T'

            fw('\t'
               'type_out->' + atom.name + ' = (' + enum_name +
               ')EXTRACT(bitstring, ' + str(atom.slice.start) + ', ' +
               str(atom.slice.length) + ');'
               '\n')
        elif atom.type.type == 'bool':
            fw('\t'
               'type_out->' + atom.name + ' = EXTRACT(bitstring, ' +
               str(atom.slice.start) + ', ' + str(atom.slice.length) + ');'
               '\n')
        else:
            if atom.type.endianness == Endianness.LITTLE:
                fw('\t'
                   'type_out->' + atom.name + ' = ' +
                   swap_endianness_fn(atom.type) + '(EXTRACT(bitstring, ' +
                   str(atom.slice.start) + ', ' + str(atom.slice.length) +
                   '));'
                   '\n')
            else:
                if atom.type.issigned():
                    fw('\t'
                       'type_out->' + atom.name +
                       ' = SIGN(EXTRACT(bitstring, ' + str(atom.slice.start) +
                       ', ' + str(atom.slice.length) + '), ' +
                       str(atom.slice.length) + ');'
                       '\n')
                else:
                    fw('\t'
                       'type_out->' + atom.name + ' = EXTRACT(bitstring, ' +
                       str(atom.slice.start) + ', ' + str(atom.slice.length) +
                       ');'
                       '\n')
Beispiel #12
0
def declare_pub_frame(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('void CANlib_Send_{}(CANlib_{}_T *inp);\n'.format(tot_name, tot_name))
Beispiel #13
0
def declare_sub_frame(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('extern CANlib_{}_T CANlib_{}_Input;\n'.format(tot_name, tot_name) +
       'void CANlib_Handle_{}(Frame *frame);\n'.format(tot_name, tot_name))
Beispiel #14
0
def define_struct(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name)
    fw('{}_T {}_Input;\n'.format(tot_name, tot_name))
Beispiel #15
0
def define_sub_frame(frame, name_prepends, fw):
    tot_name = coord(name_prepends, frame.name, prefix=False)
    fw('void CANlib_Handle_{}(Frame *frame)'.format(tot_name, tot_name) +
       ' {\n' + '\tCANlib_Unpack_{}(frame, &CANlib_{}_Input);\n'.format(
           tot_name, tot_name) + '}\n\n')