Changeset 841e6e5 in mainline


Ignore:
Timestamp:
2011-03-27T10:46:17Z (13 years ago)
Author:
Matej Klonfar <maklf@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
79e1abd
Parents:
57d9c05e
Message:

Output report creating API

Location:
uspace/lib/usb
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/usb/include/usb/classes/hidparser.h

    r57d9c05e r841e6e5  
    291291 */
    292292/** Allocates output report buffer*/
    293 uint8_t *usb_hid_report_output(usb_hid_report_parser_t *parser);
     293uint8_t *usb_hid_report_output(usb_hid_report_parser_t *parser, size_t *size);
    294294
    295295/** Frees output report buffer*/
  • uspace/lib/usb/src/hidparser.c

    r57d9c05e r841e6e5  
    7171inline size_t usb_hid_count_item_offset(usb_hid_report_item_t * report_item, size_t offset);
    7272int usb_hid_translate_data(usb_hid_report_item_t *item, const uint8_t *data, size_t j);
     73int32_t usb_hid_translate_data_reverse(usb_hid_report_item_t *item, int32_t value);
    7374int usb_pow(int a, int b);
    7475
     
    402403 * @return Error code
    403404 */
    404 
    405405int usb_hid_report_parse_global_tag(uint8_t tag, const uint8_t *data, size_t item_size,
    406406                             usb_hid_report_item_t *report_item, usb_hid_report_path_t *usage_path)
     
    11031103        }
    11041104       
    1105         // read the last outpu report item
     1105        // read the last output report item
    11061106        usb_hid_report_item_t *last;
    11071107        link_t *link;
     
    11131113
    11141114                uint8_t *buffer = malloc(sizeof(uint8_t) * (*size));
     1115                memset(buffer, 0, sizeof(uint8_t) * (*size));
     1116                usb_log_debug("output buffer: %s\n", usb_debug_str_buffer(buffer, *size, 0));
     1117
    11151118                return buffer;
    11161119        }
     
    11281131 */
    11291132void usb_hid_report_output_free(uint8_t *output)
     1133
    11301134{
    11311135        if(output != NULL) {
     
    11531157       
    11541158        item = parser->output.next;
    1155         while(&parser->input != item) {
     1159        while(&parser->output != item) {
    11561160                report_item = list_get_instance(item, usb_hid_report_item_t, link);
    11571161                if(!USB_HID_ITEM_FLAG_CONSTANT(report_item->item_flags) &&
     
    11831187                                    int32_t *data, size_t data_size)
    11841188{
    1185         //TODO
    1186         //
    1187         //go throught output descriptor and
    1188         // if path match then take data from the begin, translate them and
    1189         // or to the buffer
    1190         //
    1191         // it should be the reverse process to input translation
    1192        
    11931189        usb_hid_report_item_t *report_item;
    11941190        link_t *item;   
    11951191        size_t idx=0;
    11961192        int i=0;
    1197         int32_t field_value=0;
    11981193        int32_t value=0;
    1199         int8_t mask;
    1200         int8_t offset;
     1194        int offset;
     1195        int length;
     1196        int32_t tmp_value;
    12011197       
    12021198        if(parser == NULL) {
     
    12061202        item = parser->output.next;     
    12071203        while(item != &parser->output) {
    1208                 report_item = list_get_instance(item, usb_hid_report_item_t ,link);
    1209 
    1210                 if(idx > size) {
    1211                         return EINVAL;
     1204                report_item = list_get_instance(item, usb_hid_report_item_t, link);
     1205
     1206                for(i=0; i<report_item->count; i++, idx++) {
     1207
     1208                        if(idx >= data_size) {
     1209                                break;
     1210                        }
     1211
     1212                        // translate data
     1213                        if(USB_HID_ITEM_FLAG_CONSTANT(report_item->item_flags)) {
     1214                                value = report_item->logical_minimum;
     1215                        }
     1216                        else {
     1217                                //variable item
     1218                                value = usb_hid_translate_data_reverse(report_item, data[idx]);
     1219                        }
     1220
     1221                        if((USB_HID_ITEM_FLAG_VARIABLE(report_item->item_flags) == 0) ||
     1222                                ((report_item->usage_minimum == 0) && (report_item->usage_maximum == 0))) {
     1223//                              // variable item
     1224                                offset = report_item->offset + (i * report_item->size);
     1225                                length = report_item->size;
     1226                        }
     1227                        else {
     1228                                //bitmap
     1229                                offset = report_item->offset;
     1230                                length = report_item->size * report_item->count;
     1231                        }
     1232
     1233                        if((offset/8) == ((offset+length)/8)) {
     1234                                // je to v jednom bytu
     1235                                if(((size_t)(offset/8) >= size) || ((size_t)(offset+length)/8) >= size) {
     1236                                        break; // TODO ErrorCode
     1237                                }
     1238
     1239                                value = value << (8- ((offset+length)%8));
     1240                                value = value & (((1 << length)-1) << (8- ((offset+length)%8)));
     1241                                buffer[offset/8] = buffer[offset/8] | value;
     1242
     1243                        }
     1244                        else {
     1245                                // je to ve dvou!! FIXME: melo by to umet delsi jak 2
     1246
     1247                                // konec prvniho
     1248                                tmp_value = value;
     1249                                tmp_value = tmp_value >> (8 - (offset%8));
     1250                                tmp_value = tmp_value & ((1 << (8-(offset%8)))-1);
     1251                                buffer[offset/8] = buffer[offset/8] | tmp_value;
     1252
     1253                                // a ted druhej
     1254                                value = value & (((1 << report_item->size) - ((8 - (offset%8))))-1);
     1255                                buffer[(offset+length)/8] = buffer[(offset+length)/8] | value;
     1256                        }
     1257
    12121258                }
    12131259
    1214                 for(i=0; i<report_item->count; i++, idx++) {
    1215                         // translate data
    1216                         value = usb_hid_translate_data_output(report_item, data[idx]);
    1217 
    1218                         // pres kazdy byte v bufferu kteryho se to tyka
    1219                         for(){
    1220                                 // vybrat ktera cast value patri do tohodle bytu
    1221                                 // shiftnout podle pozice
    1222                                
    1223                                 //samotny vlozeni do bufferu
    1224                                 buffer[x+j] |= value[j];
    1225                         }                       
     1260                item = item->next;
     1261        }
     1262
     1263
     1264        return EOK;
     1265}
     1266
     1267/**
     1268 *
     1269 * @param item
     1270 * @param value
     1271 * @return
     1272 */
     1273int32_t usb_hid_translate_data_reverse(usb_hid_report_item_t *item, int value)
     1274{
     1275        int ret=0;
     1276        int resolution;
     1277
     1278        if((USB_HID_ITEM_FLAG_VARIABLE(item->item_flags) == 0) ||
     1279                ((item->usage_minimum == 0) && (item->usage_maximum == 0))) {
     1280
     1281                // variable item
     1282                if((item->physical_minimum == 0) && (item->physical_maximum == 0)) {
     1283                        item->physical_minimum = item->logical_minimum;
     1284                        item->physical_maximum = item->logical_maximum;
    12261285                }
    1227         }
    1228 
    1229         return EOK;
     1286
     1287                if(item->physical_maximum == item->physical_minimum){
     1288                    resolution = 1;
     1289                }
     1290                else {
     1291                    resolution = (item->logical_maximum - item->logical_minimum) /
     1292                        ((item->physical_maximum - item->physical_minimum) *
     1293                        (usb_pow(10,(item->unit_exponent))));
     1294                }
     1295
     1296                ret = ((value - item->physical_minimum) * resolution) + item->logical_minimum;
     1297        }
     1298        else {
     1299                // bitmapa
     1300                if(value == 0) {
     1301                        ret = 0;
     1302                }
     1303                else {
     1304                        size_t bitmap_idx = (value - item->usage_minimum);
     1305                        ret = 1 << bitmap_idx;
     1306                }
     1307        }
     1308
     1309
     1310        return ret;
    12301311}
    12311312
Note: See TracChangeset for help on using the changeset viewer.