diff --git a/applications/debug/ccid_test/ccid_test_app.c b/applications/debug/ccid_test/ccid_test_app.c index be6f631f4c2..46a1237f93d 100644 --- a/applications/debug/ccid_test/ccid_test_app.c +++ b/applications/debug/ccid_test/ccid_test_app.c @@ -133,8 +133,8 @@ void handle_instruction_01(ISO7816_Response_APDU* responseAPDU) { void handle_instruction_02( uint8_t p1, uint8_t p2, - uint8_t lc, - uint8_t le, + uint16_t lc, + uint16_t le, ISO7816_Response_APDU* responseAPDU) { if(p1 == 0 && p2 == 0 && lc == 0 && le >= 2) { responseAPDU->Data[0] = 0x62; @@ -153,7 +153,11 @@ void handle_instruction_02( //Instruction 3: sends a command with a body with two bytes, receives a response with no bytes //APDU example: 0x01:0x03:0x00:0x00:0x02:CA:FE //response SW1=0x90, SW2=0x00 -void handle_instruction_03(uint8_t p1, uint8_t p2, uint8_t lc, ISO7816_Response_APDU* responseAPDU) { +void handle_instruction_03( + uint8_t p1, + uint8_t p2, + uint16_t lc, + ISO7816_Response_APDU* responseAPDU) { if(p1 == 0 && p2 == 0 && lc == 2) { responseAPDU->DataLen = 0; iso7816_set_response(responseAPDU, ISO7816_RESPONSE_OK); @@ -170,8 +174,8 @@ void handle_instruction_03(uint8_t p1, uint8_t p2, uint8_t lc, ISO7816_Response_ void handle_instruction_04( uint8_t p1, uint8_t p2, - uint8_t lc, - uint8_t le, + uint16_t lc, + uint16_t le, const uint8_t* commandApduDataBuffer, ISO7816_Response_APDU* responseAPDU) { if(p1 == 0 && p2 == 0 && lc > 0 && le > 0 && le >= lc) { @@ -249,8 +253,10 @@ int32_t ccid_test_app(void* p) { FuriHalUsbInterface* usb_mode_prev = furi_hal_usb_get_config(); furi_hal_usb_unlock(); - furi_hal_ccid_set_callbacks((CcidCallbacks*)&ccid_cb, NULL); + furi_check(furi_hal_usb_set_config(&usb_ccid, &app->ccid_cfg) == true); + furi_hal_usb_ccid_set_callbacks((CcidCallbacks*)&ccid_cb, NULL); + furi_hal_usb_ccid_insert_smartcard(); iso7816_set_callbacks((Iso7816Callbacks*)&iso87816_cb); @@ -271,8 +277,8 @@ int32_t ccid_test_app(void* p) { } //tear down USB + furi_hal_usb_ccid_set_callbacks(NULL, NULL); furi_hal_usb_set_config(usb_mode_prev, NULL); - furi_hal_ccid_set_callbacks(NULL, NULL); iso7816_set_callbacks(NULL); diff --git a/applications/debug/ccid_test/client/ccid_client.py b/applications/debug/ccid_test/client/ccid_client.py old mode 100644 new mode 100755 index 5f43deb8741..77d2711ef94 --- a/applications/debug/ccid_test/client/ccid_client.py +++ b/applications/debug/ccid_test/client/ccid_client.py @@ -1,3 +1,4 @@ +#!/usr/bin/env python # pylint: disable=missing-module-docstring, too-many-arguments, consider-using-f-string, missing-function-docstring from smartcard.System import readers @@ -100,12 +101,14 @@ def main(): small_apdu, ) - max_apdu = list(range(0, 0x30)) + upper_bound = 0xF0 + max_apdu = list(range(0, upper_bound)) test_apdu( connection, - "INS 0x04: Lc=0x30, data=max_apdu, Le=0x30. Expect 0x30 bytes data in return", - [0x01, 0x04, 0x00, 0x00, 0x30] + max_apdu + [0x30], + "INS 0x04: Lc=0x%x, data=max_apdu, Le=0x%x. Expect 0x%x bytes data in return" + % (upper_bound, upper_bound, upper_bound), + [0x01, 0x04, 0x00, 0x00, upper_bound] + max_apdu + [upper_bound], 0x90, 0x00, max_apdu, diff --git a/applications/system/hid_app/assets/Alt_17x10.png b/applications/system/hid_app/assets/Alt_17x10.png index 93041d25039..78529ca07d7 100644 Binary files a/applications/system/hid_app/assets/Alt_17x10.png and b/applications/system/hid_app/assets/Alt_17x10.png differ diff --git a/applications/system/hid_app/assets/Alt_active_17x9.png b/applications/system/hid_app/assets/Alt_active_17x9.png new file mode 100755 index 00000000000..46a21a2e855 Binary files /dev/null and b/applications/system/hid_app/assets/Alt_active_17x9.png differ diff --git a/applications/system/hid_app/assets/Alt_pressed_17x10.png b/applications/system/hid_app/assets/Alt_pressed_17x10.png deleted file mode 100644 index e7421c8c0bf..00000000000 Binary files a/applications/system/hid_app/assets/Alt_pressed_17x10.png and /dev/null differ diff --git a/applications/system/hid_app/assets/Backspace_9x7.png b/applications/system/hid_app/assets/Backspace_9x7.png deleted file mode 100644 index e098cf67616..00000000000 Binary files a/applications/system/hid_app/assets/Backspace_9x7.png and /dev/null differ diff --git a/applications/system/hid_app/assets/Cmd_17x10.png b/applications/system/hid_app/assets/Cmd_17x10.png index 26ca3395c69..b29da07b716 100644 Binary files a/applications/system/hid_app/assets/Cmd_17x10.png and b/applications/system/hid_app/assets/Cmd_17x10.png differ diff --git a/applications/system/hid_app/assets/Cmd_active_17x9.png b/applications/system/hid_app/assets/Cmd_active_17x9.png new file mode 100755 index 00000000000..9d31b4eb3ef Binary files /dev/null and b/applications/system/hid_app/assets/Cmd_active_17x9.png differ diff --git a/applications/system/hid_app/assets/Cmd_pressed_17x10.png b/applications/system/hid_app/assets/Cmd_pressed_17x10.png deleted file mode 100644 index 274c3e070ae..00000000000 Binary files a/applications/system/hid_app/assets/Cmd_pressed_17x10.png and /dev/null differ diff --git a/applications/system/hid_app/assets/Ctrl_17x10.png b/applications/system/hid_app/assets/Ctrl_17x10.png index 0eda7216000..05be3292eba 100644 Binary files a/applications/system/hid_app/assets/Ctrl_17x10.png and b/applications/system/hid_app/assets/Ctrl_17x10.png differ diff --git a/applications/system/hid_app/assets/Ctrl_active_17x9.png b/applications/system/hid_app/assets/Ctrl_active_17x9.png new file mode 100755 index 00000000000..6fade6dd77d Binary files /dev/null and b/applications/system/hid_app/assets/Ctrl_active_17x9.png differ diff --git a/applications/system/hid_app/assets/Ctrl_pressed_17x10.png b/applications/system/hid_app/assets/Ctrl_pressed_17x10.png deleted file mode 100644 index 978a1090c2e..00000000000 Binary files a/applications/system/hid_app/assets/Ctrl_pressed_17x10.png and /dev/null differ diff --git a/applications/system/hid_app/assets/Del_17x10.png b/applications/system/hid_app/assets/Del_17x10.png index 13d73698307..95cbf7d5bd9 100644 Binary files a/applications/system/hid_app/assets/Del_17x10.png and b/applications/system/hid_app/assets/Del_17x10.png differ diff --git a/applications/system/hid_app/assets/Enter_11x7.png b/applications/system/hid_app/assets/Enter_11x7.png new file mode 100755 index 00000000000..d41b8feffbd Binary files /dev/null and b/applications/system/hid_app/assets/Enter_11x7.png differ diff --git a/applications/system/hid_app/assets/Esc_17x10.png b/applications/system/hid_app/assets/Esc_17x10.png index 6a011e97a8a..83a6f225fc6 100644 Binary files a/applications/system/hid_app/assets/Esc_17x10.png and b/applications/system/hid_app/assets/Esc_17x10.png differ diff --git a/applications/system/hid_app/assets/Shift_active_7x9.png b/applications/system/hid_app/assets/Shift_active_7x9.png new file mode 100644 index 00000000000..1ec9ce11e8a Binary files /dev/null and b/applications/system/hid_app/assets/Shift_active_7x9.png differ diff --git a/applications/system/hid_app/assets/Shift_inactive_7x9.png b/applications/system/hid_app/assets/Shift_inactive_7x9.png new file mode 100644 index 00000000000..1cd97076edc Binary files /dev/null and b/applications/system/hid_app/assets/Shift_inactive_7x9.png differ diff --git a/applications/system/hid_app/assets/Shift_pressed_7x10.png b/applications/system/hid_app/assets/Shift_pressed_7x10.png deleted file mode 100644 index 4f6b4b58eac..00000000000 Binary files a/applications/system/hid_app/assets/Shift_pressed_7x10.png and /dev/null differ diff --git a/applications/system/hid_app/assets/Tab_17x10.png b/applications/system/hid_app/assets/Tab_17x10.png index c62d75c0db5..4d8471483e5 100644 Binary files a/applications/system/hid_app/assets/Tab_17x10.png and b/applications/system/hid_app/assets/Tab_17x10.png differ diff --git a/applications/system/hid_app/assets/Tab_19x12.png b/applications/system/hid_app/assets/Tab_19x12.png new file mode 100755 index 00000000000..4dbde3babfc Binary files /dev/null and b/applications/system/hid_app/assets/Tab_19x12.png differ diff --git a/applications/system/hid_app/assets/apostrophe_button_9x11.png b/applications/system/hid_app/assets/apostrophe_button_9x11.png new file mode 100644 index 00000000000..0f54f0e2b15 Binary files /dev/null and b/applications/system/hid_app/assets/apostrophe_button_9x11.png differ diff --git a/applications/system/hid_app/assets/backslash_button_9x11.png b/applications/system/hid_app/assets/backslash_button_9x11.png new file mode 100755 index 00000000000..6cac74a57a1 Binary files /dev/null and b/applications/system/hid_app/assets/backslash_button_9x11.png differ diff --git a/applications/system/hid_app/assets/backspace_19x11.png b/applications/system/hid_app/assets/backspace_19x11.png new file mode 100755 index 00000000000..caf92807b5f Binary files /dev/null and b/applications/system/hid_app/assets/backspace_19x11.png differ diff --git a/applications/system/hid_app/assets/backspace_hovered_9x11.png b/applications/system/hid_app/assets/backspace_hovered_9x11.png new file mode 100755 index 00000000000..17cb1b7403b Binary files /dev/null and b/applications/system/hid_app/assets/backspace_hovered_9x11.png differ diff --git a/applications/system/hid_app/assets/backtick_button_9x11.png b/applications/system/hid_app/assets/backtick_button_9x11.png new file mode 100755 index 00000000000..1e5955a03ac Binary files /dev/null and b/applications/system/hid_app/assets/backtick_button_9x11.png differ diff --git a/applications/system/hid_app/assets/brace_left_button_9x11.png b/applications/system/hid_app/assets/brace_left_button_9x11.png new file mode 100755 index 00000000000..a61db48f369 Binary files /dev/null and b/applications/system/hid_app/assets/brace_left_button_9x11.png differ diff --git a/applications/system/hid_app/assets/brace_right_button_9x11.png b/applications/system/hid_app/assets/brace_right_button_9x11.png new file mode 100755 index 00000000000..bf6b927f192 Binary files /dev/null and b/applications/system/hid_app/assets/brace_right_button_9x11.png differ diff --git a/applications/system/hid_app/assets/equals_button_9x11.png b/applications/system/hid_app/assets/equals_button_9x11.png new file mode 100755 index 00000000000..8fe8afe34d3 Binary files /dev/null and b/applications/system/hid_app/assets/equals_button_9x11.png differ diff --git a/applications/system/hid_app/assets/hash_button_9x11.png b/applications/system/hid_app/assets/hash_button_9x11.png new file mode 100755 index 00000000000..bddc7aaceae Binary files /dev/null and b/applications/system/hid_app/assets/hash_button_9x11.png differ diff --git a/applications/system/hid_app/assets/percent_button_9x11.png b/applications/system/hid_app/assets/percent_button_9x11.png new file mode 100755 index 00000000000..ce12dcbf1e4 Binary files /dev/null and b/applications/system/hid_app/assets/percent_button_9x11.png differ diff --git a/applications/system/hid_app/assets/quote_button_9x11.png b/applications/system/hid_app/assets/quote_button_9x11.png new file mode 100755 index 00000000000..e96d29ddcdb Binary files /dev/null and b/applications/system/hid_app/assets/quote_button_9x11.png differ diff --git a/applications/system/hid_app/assets/slash_button_9x11.png b/applications/system/hid_app/assets/slash_button_9x11.png new file mode 100755 index 00000000000..60871320ffd Binary files /dev/null and b/applications/system/hid_app/assets/slash_button_9x11.png differ diff --git a/applications/system/hid_app/assets/sq_bracket_left_button_9x11.png b/applications/system/hid_app/assets/sq_bracket_left_button_9x11.png new file mode 100755 index 00000000000..0983db12962 Binary files /dev/null and b/applications/system/hid_app/assets/sq_bracket_left_button_9x11.png differ diff --git a/applications/system/hid_app/assets/sq_bracket_right_button_9x11.png b/applications/system/hid_app/assets/sq_bracket_right_button_9x11.png new file mode 100755 index 00000000000..48f9c77e4df Binary files /dev/null and b/applications/system/hid_app/assets/sq_bracket_right_button_9x11.png differ diff --git a/applications/system/hid_app/assets/underscore_button_9x11.png b/applications/system/hid_app/assets/underscore_button_9x11.png new file mode 100755 index 00000000000..eb000cba552 Binary files /dev/null and b/applications/system/hid_app/assets/underscore_button_9x11.png differ diff --git a/applications/system/hid_app/views/hid_keyboard.c b/applications/system/hid_app/views/hid_keyboard.c index ec95082e935..0b8c4ed3195 100644 --- a/applications/system/hid_app/views/hid_keyboard.c +++ b/applications/system/hid_app/views/hid_keyboard.c @@ -30,6 +30,7 @@ typedef struct { char key; char shift_key; const Icon* icon; + const Icon* icon_shift; const Icon* icon_toggled; uint8_t value; } HidKeyboardKey; @@ -40,10 +41,10 @@ typedef struct { } HidKeyboardPoint; // 4 BY 12 #define MARGIN_TOP 0 -#define MARGIN_LEFT 4 -#define KEY_WIDTH 9 -#define KEY_HEIGHT 12 -#define KEY_PADDING 1 +#define MARGIN_LEFT 3 +#define KEY_WIDTH 11 +#define KEY_HEIGHT 13 +#define KEY_PADDING -1 #define ROW_COUNT 7 #define COLUMN_COUNT 12 @@ -66,15 +67,23 @@ const HidKeyboardKey hid_keyboard_keyset[ROW_COUNT][COLUMN_COUNT] = { { {.width = 1, .icon = NULL, .key = '1', .shift_key = '!', .value = HID_KEYBOARD_1}, {.width = 1, .icon = NULL, .key = '2', .shift_key = '@', .value = HID_KEYBOARD_2}, - {.width = 1, .icon = NULL, .key = '3', .shift_key = '#', .value = HID_KEYBOARD_3}, + {.width = 1, + .icon = NULL, + .icon_shift = &I_hash_button_9x11, + .key = '3', + .value = HID_KEYBOARD_3}, {.width = 1, .icon = NULL, .key = '4', .shift_key = '$', .value = HID_KEYBOARD_4}, - {.width = 1, .icon = NULL, .key = '5', .shift_key = '%', .value = HID_KEYBOARD_5}, + {.width = 1, + .icon = NULL, + .icon_shift = &I_percent_button_9x11, + .key = '5', + .value = HID_KEYBOARD_5}, {.width = 1, .icon = NULL, .key = '6', .shift_key = '^', .value = HID_KEYBOARD_6}, {.width = 1, .icon = NULL, .key = '7', .shift_key = '&', .value = HID_KEYBOARD_7}, {.width = 1, .icon = NULL, .key = '8', .shift_key = '*', .value = HID_KEYBOARD_8}, {.width = 1, .icon = NULL, .key = '9', .shift_key = '(', .value = HID_KEYBOARD_9}, {.width = 1, .icon = NULL, .key = '0', .shift_key = ')', .value = HID_KEYBOARD_0}, - {.width = 2, .icon = &I_Backspace_9x7, .value = HID_KEYBOARD_DELETE}, + {.width = 2, .icon = &I_backspace_19x11, .value = HID_KEYBOARD_DELETE}, {.width = 0, .value = HID_KEYBOARD_DELETE}, }, { @@ -88,11 +97,13 @@ const HidKeyboardKey hid_keyboard_keyset[ROW_COUNT][COLUMN_COUNT] = { {.width = 1, .icon = NULL, .key = 'i', .shift_key = 'I', .value = HID_KEYBOARD_I}, {.width = 1, .icon = NULL, .key = 'o', .shift_key = 'O', .value = HID_KEYBOARD_O}, {.width = 1, .icon = NULL, .key = 'p', .shift_key = 'P', .value = HID_KEYBOARD_P}, - {.width = 1, .icon = NULL, .key = '[', .shift_key = '{', .value = HID_KEYBOARD_OPEN_BRACKET}, {.width = 1, - .icon = NULL, - .key = ']', - .shift_key = '}', + .icon = &I_sq_bracket_left_button_9x11, + .icon_shift = &I_brace_left_button_9x11, + .value = HID_KEYBOARD_OPEN_BRACKET}, + {.width = 1, + .icon = &I_sq_bracket_right_button_9x11, + .icon_shift = &I_brace_right_button_9x11, .value = HID_KEYBOARD_CLOSE_BRACKET}, }, { @@ -117,16 +128,26 @@ const HidKeyboardKey hid_keyboard_keyset[ROW_COUNT][COLUMN_COUNT] = { {.width = 1, .icon = NULL, .key = 'b', .shift_key = 'B', .value = HID_KEYBOARD_B}, {.width = 1, .icon = NULL, .key = 'n', .shift_key = 'N', .value = HID_KEYBOARD_N}, {.width = 1, .icon = NULL, .key = 'm', .shift_key = 'M', .value = HID_KEYBOARD_M}, - {.width = 1, .icon = NULL, .key = '/', .shift_key = '?', .value = HID_KEYBOARD_SLASH}, - {.width = 1, .icon = NULL, .key = '\\', .shift_key = '|', .value = HID_KEYBOARD_BACKSLASH}, - {.width = 1, .icon = NULL, .key = '`', .shift_key = '~', .value = HID_KEYBOARD_GRAVE_ACCENT}, + {.width = 1, .icon = &I_slash_button_9x11, .shift_key = '?', .value = HID_KEYBOARD_SLASH}, + {.width = 1, + .icon = &I_backslash_button_9x11, + .shift_key = '|', + .value = HID_KEYBOARD_BACKSLASH}, + {.width = 1, + .icon = &I_backtick_button_9x11, + .shift_key = '~', + .value = HID_KEYBOARD_GRAVE_ACCENT}, {.width = 1, .icon = &I_ButtonUp_7x4, .value = HID_KEYBOARD_UP_ARROW}, - {.width = 1, .icon = NULL, .key = '-', .shift_key = '_', .value = HID_KEYBOARD_MINUS}, + {.width = 1, + .icon = NULL, + .icon_shift = &I_underscore_button_9x11, + .key = '-', + .value = HID_KEYBOARD_MINUS}, }, { {.width = 1, - .icon = &I_Pin_arrow_up_7x9, - .icon_toggled = &I_Shift_pressed_7x10, + .icon = &I_Shift_inactive_7x9, + .icon_toggled = &I_Shift_active_7x9, .value = HID_KEYBOARD_L_SHIFT}, {.width = 1, .icon = NULL, .key = ',', .shift_key = '<', .value = HID_KEYBOARD_COMMA}, {.width = 1, .icon = NULL, .key = '.', .shift_key = '>', .value = HID_KEYBOARD_DOT}, @@ -134,8 +155,14 @@ const HidKeyboardKey hid_keyboard_keyset[ROW_COUNT][COLUMN_COUNT] = { {.width = 0, .value = HID_KEYBOARD_SPACEBAR}, {.width = 0, .value = HID_KEYBOARD_SPACEBAR}, {.width = 0, .value = HID_KEYBOARD_SPACEBAR}, - {.width = 1, .icon = NULL, .key = '\'', .shift_key = '\"', .value = HID_KEYBOARD_APOSTROPHE}, - {.width = 1, .icon = NULL, .key = '=', .shift_key = '+', .value = HID_KEYBOARD_EQUAL_SIGN}, + {.width = 1, + .icon = &I_apostrophe_button_9x11, + .icon_shift = &I_quote_button_9x11, + .value = HID_KEYBOARD_APOSTROPHE}, + {.width = 1, + .icon = &I_equals_button_9x11, + .shift_key = '+', + .value = HID_KEYBOARD_EQUAL_SIGN}, {.width = 1, .icon = &I_ButtonLeft_4x7, .value = HID_KEYBOARD_LEFT_ARROW}, {.width = 1, .icon = &I_ButtonDown_7x4, .value = HID_KEYBOARD_DOWN_ARROW}, {.width = 1, .icon = &I_ButtonRight_4x7, .value = HID_KEYBOARD_RIGHT_ARROW}, @@ -143,17 +170,17 @@ const HidKeyboardKey hid_keyboard_keyset[ROW_COUNT][COLUMN_COUNT] = { { {.width = 2, .icon = &I_Ctrl_17x10, - .icon_toggled = &I_Ctrl_pressed_17x10, + .icon_toggled = &I_Ctrl_active_17x9, .value = HID_KEYBOARD_L_CTRL}, {.width = 0, .value = HID_KEYBOARD_L_CTRL}, {.width = 2, .icon = &I_Alt_17x10, - .icon_toggled = &I_Alt_pressed_17x10, + .icon_toggled = &I_Alt_active_17x9, .value = HID_KEYBOARD_L_ALT}, {.width = 0, .value = HID_KEYBOARD_L_ALT}, {.width = 2, .icon = &I_Cmd_17x10, - .icon_toggled = &I_Cmd_pressed_17x10, + .icon_toggled = &I_Cmd_active_17x9, .value = HID_KEYBOARD_L_GUI}, {.width = 0, .value = HID_KEYBOARD_L_GUI}, {.width = 2, .icon = &I_Tab_17x10, .value = HID_KEYBOARD_TAB}, @@ -194,8 +221,47 @@ static void hid_keyboard_draw_key( keyWidth, KEY_HEIGHT); } + + if(model->shift && key.icon_shift != NULL) { + // Icon and shift + const Icon* key_icon = key.icon_shift; + + if((model->ctrl && key.value == HID_KEYBOARD_L_CTRL) || + (model->alt && key.value == HID_KEYBOARD_L_ALT) || + (key.value == HID_KEYBOARD_L_SHIFT) || + (model->gui && key.value == HID_KEYBOARD_L_GUI)) { + if(key.icon_toggled) { + key_icon = key.icon_toggled; + } + } + // Draw the icon centered on the button + canvas_draw_icon( + canvas, + MARGIN_LEFT + x * (KEY_WIDTH + KEY_PADDING) + keyWidth / 2 - key_icon->width / 2, + MARGIN_TOP + y * (KEY_HEIGHT + KEY_PADDING) + KEY_HEIGHT / 2 - key_icon->height / 2, + key_icon); + + return; + } + if(model->shift && key.shift_key != 0) { + // Text and shift + char key_str[2] = {key.shift_key, '\0'}; + + canvas_draw_str_aligned( + canvas, + MARGIN_LEFT + x * (KEY_WIDTH + KEY_PADDING) + keyWidth / 2 + 1, + MARGIN_TOP + y * (KEY_HEIGHT + KEY_PADDING) + KEY_HEIGHT / 2 + 1, + AlignCenter, + AlignCenter, + key_str); + + return; + } + if(key.icon != NULL) { + // Icon with no shift const Icon* key_icon = key.icon; + if((model->ctrl && key.value == HID_KEYBOARD_L_CTRL) || (model->alt && key.value == HID_KEYBOARD_L_ALT) || (model->shift && key.value == HID_KEYBOARD_L_SHIFT) || @@ -210,17 +276,29 @@ static void hid_keyboard_draw_key( MARGIN_LEFT + x * (KEY_WIDTH + KEY_PADDING) + keyWidth / 2 - key_icon->width / 2, MARGIN_TOP + y * (KEY_HEIGHT + KEY_PADDING) + KEY_HEIGHT / 2 - key_icon->height / 2, key_icon); - } else { - char key_str[2] = "\0\0"; - // If shift is toggled use the shift key when available - key_str[0] = (model->shift && key.shift_key != 0) ? key.shift_key : key.key; + + return; + } + + if(key.key != 0) { + // Text with no shift + char key_str[2] = {key.key, '\0'}; + uint8_t key_offset = 0; + + // Special case for numbers, draw them one pixel lower + if(key.value >= HID_KEYBOARD_1 && key.value <= HID_KEYBOARD_0) { + key_offset = 1; + } + canvas_draw_str_aligned( canvas, MARGIN_LEFT + x * (KEY_WIDTH + KEY_PADDING) + keyWidth / 2 + 1, - MARGIN_TOP + y * (KEY_HEIGHT + KEY_PADDING) + KEY_HEIGHT / 2, + MARGIN_TOP + y * (KEY_HEIGHT + KEY_PADDING) + KEY_HEIGHT / 2 + key_offset, AlignCenter, AlignCenter, key_str); + + return; } } diff --git a/targets/f18/api_symbols.csv b/targets/f18/api_symbols.csv index ae561c98c00..7e254ce4010 100644 --- a/targets/f18/api_symbols.csv +++ b/targets/f18/api_symbols.csv @@ -1,5 +1,5 @@ entry,status,name,type,params -Version,+,68.1,, +Version,+,69.0,, Header,+,applications/services/bt/bt_service/bt.h,, Header,+,applications/services/bt/bt_service/bt_keys_storage.h,, Header,+,applications/services/cli/cli.h,, @@ -1178,9 +1178,6 @@ Function,+,furi_hal_bus_enable,void,FuriHalBus Function,+,furi_hal_bus_init_early,void, Function,+,furi_hal_bus_is_enabled,_Bool,FuriHalBus Function,+,furi_hal_bus_reset,void,FuriHalBus -Function,+,furi_hal_ccid_ccid_insert_smartcard,void, -Function,+,furi_hal_ccid_ccid_remove_smartcard,void, -Function,+,furi_hal_ccid_set_callbacks,void,"CcidCallbacks*, void*" Function,+,furi_hal_cdc_get_ctrl_line_state,uint8_t,uint8_t Function,+,furi_hal_cdc_get_port_settings,usb_cdc_line_coding*,uint8_t Function,+,furi_hal_cdc_receive,int32_t,"uint8_t, uint8_t*, uint16_t" @@ -1454,6 +1451,9 @@ Function,-,furi_hal_spi_config_init_early,void, Function,-,furi_hal_spi_dma_init,void, Function,+,furi_hal_spi_release,void,FuriHalSpiBusHandle* Function,+,furi_hal_switch,void,void* +Function,+,furi_hal_usb_ccid_insert_smartcard,void, +Function,+,furi_hal_usb_ccid_remove_smartcard,void, +Function,+,furi_hal_usb_ccid_set_callbacks,void,"CcidCallbacks*, void*" Function,+,furi_hal_usb_disable,void, Function,+,furi_hal_usb_enable,void, Function,+,furi_hal_usb_get_config,FuriHalUsbInterface*, diff --git a/targets/f7/api_symbols.csv b/targets/f7/api_symbols.csv index f4c7a84e16d..cce5a320ab5 100644 --- a/targets/f7/api_symbols.csv +++ b/targets/f7/api_symbols.csv @@ -1,5 +1,5 @@ entry,status,name,type,params -Version,+,68.1,, +Version,+,69.0,, Header,+,applications/drivers/subghz/cc1101_ext/cc1101_ext_interconnect.h,, Header,+,applications/services/bt/bt_service/bt.h,, Header,+,applications/services/bt/bt_service/bt_keys_storage.h,, @@ -1283,9 +1283,6 @@ Function,+,furi_hal_bus_enable,void,FuriHalBus Function,+,furi_hal_bus_init_early,void, Function,+,furi_hal_bus_is_enabled,_Bool,FuriHalBus Function,+,furi_hal_bus_reset,void,FuriHalBus -Function,+,furi_hal_ccid_ccid_insert_smartcard,void, -Function,+,furi_hal_ccid_ccid_remove_smartcard,void, -Function,+,furi_hal_ccid_set_callbacks,void,"CcidCallbacks*, void*" Function,+,furi_hal_cdc_get_ctrl_line_state,uint8_t,uint8_t Function,+,furi_hal_cdc_get_port_settings,usb_cdc_line_coding*,uint8_t Function,+,furi_hal_cdc_receive,int32_t,"uint8_t, uint8_t*, uint16_t" @@ -1668,6 +1665,9 @@ Function,+,furi_hal_subghz_stop_async_tx,void, Function,+,furi_hal_subghz_tx,_Bool, Function,+,furi_hal_subghz_write_packet,void,"const uint8_t*, uint8_t" Function,+,furi_hal_switch,void,void* +Function,+,furi_hal_usb_ccid_insert_smartcard,void, +Function,+,furi_hal_usb_ccid_remove_smartcard,void, +Function,+,furi_hal_usb_ccid_set_callbacks,void,"CcidCallbacks*, void*" Function,+,furi_hal_usb_disable,void, Function,+,furi_hal_usb_enable,void, Function,+,furi_hal_usb_get_config,FuriHalUsbInterface*, diff --git a/targets/f7/furi_hal/furi_hal_usb_ccid.c b/targets/f7/furi_hal/furi_hal_usb_ccid.c index 7ce60f61e0b..a2c1a0583e5 100644 --- a/targets/f7/furi_hal/furi_hal_usb_ccid.c +++ b/targets/f7/furi_hal/furi_hal_usb_ccid.c @@ -4,28 +4,27 @@ #include #include -#include "usb.h" -#include "usb_ccid.h" +#include -static const uint8_t USB_DEVICE_NO_CLASS = 0x0; -static const uint8_t USB_DEVICE_NO_SUBCLASS = 0x0; -static const uint8_t USB_DEVICE_NO_PROTOCOL = 0x0; +#define USB_DEVICE_NO_CLASS (0x0) +#define USB_DEVICE_NO_SUBCLASS (0x0) +#define USB_DEVICE_NO_PROTOCOL (0x0) -#define FIXED_CONTROL_ENDPOINT_SIZE 8 -#define IF_NUM_MAX 1 +#define FIXED_CONTROL_ENDPOINT_SIZE (8) +#define IF_NUM_MAX (1) -#define CCID_VID_DEFAULT 0x1234 -#define CCID_PID_DEFAULT 0xABCD -#define CCID_TOTAL_SLOTS 1 -#define CCID_SLOT_INDEX 0 +#define CCID_VID_DEFAULT (0x1234) +#define CCID_PID_DEFAULT (0xABCD) +#define CCID_TOTAL_SLOTS (1) +#define CCID_SLOT_INDEX (0) #define CCID_DATABLOCK_SIZE \ (4 + 1 + CCID_SHORT_APDU_SIZE + 1) //APDU Header + Lc + Short APDU size + Le -#define ENDPOINT_DIR_IN 0x80 -#define ENDPOINT_DIR_OUT 0x00 +#define ENDPOINT_DIR_IN (0x80) +#define ENDPOINT_DIR_OUT (0x00) -#define INTERFACE_ID_CCID 0 +#define INTERFACE_ID_CCID (0) #define CCID_IN_EPADDR (ENDPOINT_DIR_IN | 2) @@ -65,6 +64,18 @@ enum CCID_Features_ExchangeLevel_t { CCID_Features_ExchangeLevel_ShortExtendedAPDU = 0x00040000 }; +typedef enum { + WorkerEvtStop = (1 << 0), + WorkerEvtRequest = (1 << 1), +} WorkerEvtFlags; + +typedef struct ccid_bulk_message_header { + uint8_t bMessageType; + uint32_t dwLength; + uint8_t bSlot; + uint8_t bSeq; +} FURI_PACKED ccid_bulk_message_header_t; + /* Device descriptor */ static struct usb_device_descriptor ccid_device_desc = { .bLength = sizeof(struct usb_device_descriptor), @@ -163,6 +174,7 @@ static void ccid_init(usbd_device* dev, FuriHalUsbInterface* intf, void* ctx); static void ccid_deinit(usbd_device* dev); static void ccid_on_wakeup(usbd_device* dev); static void ccid_on_suspend(usbd_device* dev); +static int32_t ccid_worker(void* context); FuriHalUsbInterface usb_ccid = { .init = ccid_init, @@ -181,11 +193,22 @@ FuriHalUsbInterface usb_ccid = { static usbd_respond ccid_ep_config(usbd_device* dev, uint8_t cfg); static usbd_respond ccid_control(usbd_device* dev, usbd_ctlreq* req, usbd_rqc_callback* callback); -static usbd_device* usb_dev; -static bool connected = false; -static bool smartcard_inserted = true; -static CcidCallbacks* callbacks[CCID_TOTAL_SLOTS] = {NULL}; -static void* cb_ctx[CCID_TOTAL_SLOTS]; + +typedef struct { + bool connected; + bool smartcard_inserted; + CcidCallbacks* callbacks[CCID_TOTAL_SLOTS]; + void* cb_ctx[CCID_TOTAL_SLOTS]; + FuriThread* ccid_thread; + FuriSemaphore* ccid_semaphore; + usbd_device* usb_dev; + + uint16_t receive_buffer_data_index; + uint8_t send_buffer[sizeof(ccid_bulk_message_header_t) + CCID_DATABLOCK_SIZE]; + uint8_t receive_buffer[sizeof(ccid_bulk_message_header_t) + CCID_DATABLOCK_SIZE]; +} FuriHalUsbCcid; + +static FuriHalUsbCcid* furi_hal_usb_ccid = NULL; static void* ccid_set_string_descr(char* str) { furi_check(str); @@ -205,7 +228,11 @@ static void ccid_init(usbd_device* dev, FuriHalUsbInterface* intf, void* ctx) { FuriHalUsbCcidConfig* cfg = (FuriHalUsbCcidConfig*)ctx; - usb_dev = dev; + furi_check(furi_hal_usb_ccid == NULL); + furi_hal_usb_ccid = malloc(sizeof(FuriHalUsbCcid)); + + furi_hal_usb_ccid->usb_dev = dev; + furi_hal_usb_ccid->ccid_semaphore = furi_semaphore_alloc(1, 1); usb_ccid.dev_descr->iManufacturer = 0; usb_ccid.dev_descr->iProduct = 0; @@ -233,42 +260,50 @@ static void ccid_init(usbd_device* dev, FuriHalUsbInterface* intf, void* ctx) { usbd_reg_control(dev, ccid_control); usbd_connect(dev, true); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + furi_hal_usb_ccid->ccid_thread = furi_thread_alloc_ex("CcidWorker", 2048, ccid_worker, ctx); + furi_thread_start(furi_hal_usb_ccid->ccid_thread); } static void ccid_deinit(usbd_device* dev) { + furi_thread_flags_set(furi_thread_get_id(furi_hal_usb_ccid->ccid_thread), WorkerEvtStop); + furi_thread_join(furi_hal_usb_ccid->ccid_thread); + furi_thread_free(furi_hal_usb_ccid->ccid_thread); + usbd_reg_config(dev, NULL); usbd_reg_control(dev, NULL); free(usb_ccid.str_prod_descr); free(usb_ccid.str_serial_descr); + + free(furi_hal_usb_ccid); + + furi_hal_usb_ccid = NULL; } static void ccid_on_wakeup(usbd_device* dev) { UNUSED(dev); - connected = true; + furi_check(furi_hal_usb_ccid); + + furi_hal_usb_ccid->connected = true; } static void ccid_on_suspend(usbd_device* dev) { UNUSED(dev); - connected = false; -} + furi_check(furi_hal_usb_ccid); -typedef struct ccid_bulk_message_header { - uint8_t bMessageType; - uint32_t dwLength; - uint8_t bSlot; - uint8_t bSeq; -} FURI_PACKED ccid_bulk_message_header_t; - -uint8_t SendBuffer[sizeof(ccid_bulk_message_header_t) + CCID_DATABLOCK_SIZE]; - -//stores the data p -uint8_t ReceiveBuffer[sizeof(ccid_bulk_message_header_t) + CCID_DATABLOCK_SIZE]; + furi_hal_usb_ccid->connected = false; +} void CALLBACK_CCID_GetSlotStatus( uint8_t slot, uint8_t seq, struct rdr_to_pc_slot_status* responseSlotStatus) { + furi_check(responseSlotStatus); + + furi_check(furi_hal_usb_ccid); + responseSlotStatus->bMessageType = RDR_TO_PC_SLOTSTATUS; responseSlotStatus->bSlot = slot; @@ -279,7 +314,7 @@ void CALLBACK_CCID_GetSlotStatus( if(responseSlotStatus->bSlot == CCID_SLOT_INDEX) { responseSlotStatus->bError = CCID_ERROR_NOERROR; - if(smartcard_inserted) { + if(furi_hal_usb_ccid->smartcard_inserted) { responseSlotStatus->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR | CCID_ICCSTATUS_PRESENTANDACTIVE; } else { @@ -293,9 +328,16 @@ void CALLBACK_CCID_GetSlotStatus( } void CALLBACK_CCID_SetParametersT0( + struct pc_to_rdr_set_parameters_t0* requestSetParametersT0, struct rdr_to_pc_parameters_t0* responseSetParametersT0) { + furi_check(requestSetParametersT0); + furi_check(responseSetParametersT0); + + furi_check(furi_hal_usb_ccid); + furi_check(requestSetParametersT0->bProtocolNum == 0x00); //T0 + responseSetParametersT0->bMessageType = RDR_TO_PC_PARAMETERS; responseSetParametersT0->bSlot = requestSetParametersT0->bSlot; responseSetParametersT0->bSeq = requestSetParametersT0->bSeq; @@ -305,7 +347,7 @@ void CALLBACK_CCID_SetParametersT0( if(responseSetParametersT0->bSlot == CCID_SLOT_INDEX) { responseSetParametersT0->bError = CCID_ERROR_NOERROR; - if(smartcard_inserted) { + if(furi_hal_usb_ccid->smartcard_inserted) { responseSetParametersT0->bProtocolNum = requestSetParametersT0->bProtocolNum; responseSetParametersT0->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR | CCID_ICCSTATUS_PRESENTANDACTIVE; @@ -323,6 +365,10 @@ void CALLBACK_CCID_IccPowerOn( uint8_t slot, uint8_t seq, struct rdr_to_pc_data_block* responseDataBlock) { + furi_check(responseDataBlock); + + furi_check(furi_hal_usb_ccid); + responseDataBlock->bMessageType = RDR_TO_PC_DATABLOCK; responseDataBlock->dwLength = 0; responseDataBlock->bSlot = slot; @@ -330,12 +376,12 @@ void CALLBACK_CCID_IccPowerOn( if(responseDataBlock->bSlot == CCID_SLOT_INDEX) { responseDataBlock->bError = CCID_ERROR_NOERROR; - if(smartcard_inserted) { - if(callbacks[CCID_SLOT_INDEX] != NULL) { - callbacks[CCID_SLOT_INDEX]->icc_power_on_callback( + if(furi_hal_usb_ccid->smartcard_inserted) { + if(furi_hal_usb_ccid->callbacks[CCID_SLOT_INDEX] != NULL) { + furi_hal_usb_ccid->callbacks[CCID_SLOT_INDEX]->icc_power_on_callback( responseDataBlock->abData, &responseDataBlock->dwLength, - cb_ctx[CCID_SLOT_INDEX]); + furi_hal_usb_ccid->cb_ctx[CCID_SLOT_INDEX]); responseDataBlock->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR | CCID_ICCSTATUS_PRESENTANDACTIVE; } else { @@ -355,6 +401,11 @@ void CALLBACK_CCID_IccPowerOn( void CALLBACK_CCID_XfrBlock( struct pc_to_rdr_xfr_block* receivedXfrBlock, struct rdr_to_pc_data_block* responseDataBlock) { + furi_check(receivedXfrBlock); + furi_check(responseDataBlock); + + furi_check(furi_hal_usb_ccid); + responseDataBlock->bMessageType = RDR_TO_PC_DATABLOCK; responseDataBlock->bSlot = receivedXfrBlock->bSlot; responseDataBlock->bSeq = receivedXfrBlock->bSeq; @@ -362,14 +413,14 @@ void CALLBACK_CCID_XfrBlock( if(responseDataBlock->bSlot == CCID_SLOT_INDEX) { responseDataBlock->bError = CCID_ERROR_NOERROR; - if(smartcard_inserted) { - if(callbacks[CCID_SLOT_INDEX] != NULL) { - callbacks[CCID_SLOT_INDEX]->xfr_datablock_callback( + if(furi_hal_usb_ccid->smartcard_inserted) { + if(furi_hal_usb_ccid->callbacks[CCID_SLOT_INDEX] != NULL) { + furi_hal_usb_ccid->callbacks[CCID_SLOT_INDEX]->xfr_datablock_callback( (const uint8_t*)receivedXfrBlock->abData, receivedXfrBlock->dwLength, responseDataBlock->abData, &responseDataBlock->dwLength, - cb_ctx[CCID_SLOT_INDEX]); + furi_hal_usb_ccid->cb_ctx[CCID_SLOT_INDEX]); responseDataBlock->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR | CCID_ICCSTATUS_PRESENTANDACTIVE; } else { @@ -386,116 +437,175 @@ void CALLBACK_CCID_XfrBlock( } } -void furi_hal_ccid_ccid_insert_smartcard(void) { - smartcard_inserted = true; +void furi_hal_usb_ccid_insert_smartcard(void) { + furi_check(furi_hal_usb_ccid); + + furi_hal_usb_ccid->smartcard_inserted = true; +} + +void furi_hal_usb_ccid_remove_smartcard(void) { + furi_check(furi_hal_usb_ccid); + + furi_hal_usb_ccid->smartcard_inserted = false; +} + +void furi_hal_usb_ccid_set_callbacks(CcidCallbacks* cb, void* context) { + furi_check(furi_hal_usb_ccid); + + furi_hal_usb_ccid->callbacks[CCID_SLOT_INDEX] = cb; + furi_hal_usb_ccid->cb_ctx[CCID_SLOT_INDEX] = context; } -void furi_hal_ccid_ccid_remove_smartcard(void) { - smartcard_inserted = false; +void ccid_send_packet(uint8_t* data, uint8_t len) { + furi_check(furi_hal_usb_ccid); + + if(furi_hal_usb_ccid->ccid_semaphore == NULL || furi_hal_usb_ccid->connected == false) return; + furi_check( + furi_semaphore_acquire(furi_hal_usb_ccid->ccid_semaphore, FuriWaitForever) == + FuriStatusOk); + if(furi_hal_usb_ccid->connected == true) { + usbd_ep_write(furi_hal_usb_ccid->usb_dev, CCID_IN_EPADDR, data, len); + } } -void furi_hal_ccid_set_callbacks(CcidCallbacks* cb, void* context) { - callbacks[CCID_SLOT_INDEX] = cb; - cb_ctx[CCID_SLOT_INDEX] = context; +void ccid_send_response(uint8_t* data, uint32_t len) { + uint32_t data_to_send = len; + uint32_t data_index = 0; + while(data_to_send >= CCID_EPSIZE) { + ccid_send_packet(&data[data_index], CCID_EPSIZE); + data_to_send = data_to_send - CCID_EPSIZE; + data_index = data_index + CCID_EPSIZE; + } + + ccid_send_packet(&data[data_index], data_to_send); } static void ccid_rx_ep_callback(usbd_device* dev, uint8_t event, uint8_t ep) { UNUSED(dev); UNUSED(event); UNUSED(ep); + furi_check(furi_hal_usb_ccid); + + furi_semaphore_release(furi_hal_usb_ccid->ccid_semaphore); } static void ccid_tx_ep_callback(usbd_device* dev, uint8_t event, uint8_t ep) { UNUSED(dev); - + UNUSED(ep); if(event == usbd_evt_eprx) { - if(connected == false) return; + furi_check(furi_hal_usb_ccid); + int32_t bytes_read = usbd_ep_read( + furi_hal_usb_ccid->usb_dev, + CCID_OUT_EPADDR, + &furi_hal_usb_ccid->receive_buffer[furi_hal_usb_ccid->receive_buffer_data_index], + CCID_EPSIZE); - //read initial CCID message header + if(bytes_read > 0) { + furi_hal_usb_ccid->receive_buffer_data_index = + furi_hal_usb_ccid->receive_buffer_data_index + bytes_read; - int32_t bytes_read = usbd_ep_read( - usb_dev, ep, &ReceiveBuffer, sizeof(ccid_bulk_message_header_t) + CCID_DATABLOCK_SIZE); - //minimum request size is header size - furi_check((uint16_t)bytes_read >= sizeof(ccid_bulk_message_header_t)); - ccid_bulk_message_header_t* message = (ccid_bulk_message_header_t*)&ReceiveBuffer; //-V641 - - if(message->bMessageType == PC_TO_RDR_ICCPOWERON) { - struct pc_to_rdr_icc_power_on* requestDataBlock = - (struct pc_to_rdr_icc_power_on*)message; //-V641 - struct rdr_to_pc_data_block* responseDataBlock = - (struct rdr_to_pc_data_block*)&SendBuffer; - - CALLBACK_CCID_IccPowerOn( - requestDataBlock->bSlot, requestDataBlock->bSeq, responseDataBlock); - - usbd_ep_write( - usb_dev, - CCID_IN_EPADDR, - responseDataBlock, - sizeof(struct rdr_to_pc_data_block) + - (sizeof(uint8_t) * responseDataBlock->dwLength)); - } else if(message->bMessageType == PC_TO_RDR_ICCPOWEROFF) { - struct pc_to_rdr_icc_power_off* requestIccPowerOff = - (struct pc_to_rdr_icc_power_off*)message; //-V641 - struct rdr_to_pc_slot_status* responseSlotStatus = - (struct rdr_to_pc_slot_status*)&SendBuffer; //-V641 - - CALLBACK_CCID_GetSlotStatus( - requestIccPowerOff->bSlot, requestIccPowerOff->bSeq, responseSlotStatus); - - usbd_ep_write( - usb_dev, CCID_IN_EPADDR, responseSlotStatus, sizeof(struct rdr_to_pc_slot_status)); - } else if(message->bMessageType == PC_TO_RDR_GETSLOTSTATUS) { - struct pc_to_rdr_get_slot_status* requestSlotStatus = - (struct pc_to_rdr_get_slot_status*)message; //-V641 - struct rdr_to_pc_slot_status* responseSlotStatus = - (struct rdr_to_pc_slot_status*)&SendBuffer; //-V641 - - CALLBACK_CCID_GetSlotStatus( - requestSlotStatus->bSlot, requestSlotStatus->bSeq, responseSlotStatus); - - usbd_ep_write( - usb_dev, CCID_IN_EPADDR, responseSlotStatus, sizeof(struct rdr_to_pc_slot_status)); - } else if(message->bMessageType == PC_TO_RDR_XFRBLOCK) { - struct pc_to_rdr_xfr_block* receivedXfrBlock = (struct pc_to_rdr_xfr_block*)message; - struct rdr_to_pc_data_block* responseDataBlock = - (struct rdr_to_pc_data_block*)&SendBuffer; - - furi_check(receivedXfrBlock->dwLength <= CCID_DATABLOCK_SIZE); - furi_check( - (uint16_t)bytes_read >= - sizeof(ccid_bulk_message_header_t) + receivedXfrBlock->dwLength); - - CALLBACK_CCID_XfrBlock(receivedXfrBlock, responseDataBlock); - - furi_check(responseDataBlock->dwLength <= CCID_DATABLOCK_SIZE); - - usbd_ep_write( - usb_dev, - CCID_IN_EPADDR, - responseDataBlock, - sizeof(struct rdr_to_pc_data_block) + - (sizeof(uint8_t) * responseDataBlock->dwLength)); - } else if(message->bMessageType == PC_TO_RDR_SETPARAMETERS) { - struct pc_to_rdr_set_parameters_t0* requestSetParametersT0 = - (struct pc_to_rdr_set_parameters_t0*)message; //-V641 - struct rdr_to_pc_parameters_t0* responseSetParametersT0 = - (struct rdr_to_pc_parameters_t0*)&SendBuffer; //-V641 - - furi_check(requestSetParametersT0->dwLength <= CCID_DATABLOCK_SIZE); - furi_check( - (uint16_t)bytes_read >= - sizeof(ccid_bulk_message_header_t) + requestSetParametersT0->dwLength); - - CALLBACK_CCID_SetParametersT0(requestSetParametersT0, responseSetParametersT0); - - usbd_ep_write( - usb_dev, - CCID_IN_EPADDR, - responseSetParametersT0, - sizeof(struct rdr_to_pc_parameters_t0)); + furi_thread_flags_set( + furi_thread_get_id(furi_hal_usb_ccid->ccid_thread), WorkerEvtRequest); + } + } +} + +static int32_t ccid_worker(void* context) { + UNUSED(context); + + while(1) { + furi_check(furi_hal_usb_ccid); + uint32_t flags = furi_thread_flags_wait( + WorkerEvtStop | WorkerEvtRequest, FuriFlagWaitAny, FuriWaitForever); + + if(flags & WorkerEvtRequest) { + //read initial CCID message header + + ccid_bulk_message_header_t* message = + (ccid_bulk_message_header_t*)&furi_hal_usb_ccid->receive_buffer; //-V641 + + furi_check(message); + + if(message->bMessageType == PC_TO_RDR_ICCPOWERON) { + struct pc_to_rdr_icc_power_on* requestDataBlock = + (struct pc_to_rdr_icc_power_on*)message; //-V641 + struct rdr_to_pc_data_block* responseDataBlock = + (struct rdr_to_pc_data_block*)&furi_hal_usb_ccid->send_buffer; + + CALLBACK_CCID_IccPowerOn( + requestDataBlock->bSlot, requestDataBlock->bSeq, responseDataBlock); + + ccid_send_response( + furi_hal_usb_ccid->send_buffer, + sizeof(struct rdr_to_pc_data_block) + + (sizeof(uint8_t) * responseDataBlock->dwLength)); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + + } else if(message->bMessageType == PC_TO_RDR_ICCPOWEROFF) { + struct pc_to_rdr_icc_power_off* requestIccPowerOff = + (struct pc_to_rdr_icc_power_off*)message; //-V641 + struct rdr_to_pc_slot_status* responseSlotStatus = + (struct rdr_to_pc_slot_status*)&furi_hal_usb_ccid->send_buffer; //-V641 + + CALLBACK_CCID_GetSlotStatus( + requestIccPowerOff->bSlot, requestIccPowerOff->bSeq, responseSlotStatus); + + ccid_send_response( + furi_hal_usb_ccid->send_buffer, sizeof(struct rdr_to_pc_slot_status)); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + + } else if(message->bMessageType == PC_TO_RDR_GETSLOTSTATUS) { + struct pc_to_rdr_get_slot_status* requestSlotStatus = + (struct pc_to_rdr_get_slot_status*)message; //-V641 + struct rdr_to_pc_slot_status* responseSlotStatus = + (struct rdr_to_pc_slot_status*)&furi_hal_usb_ccid->send_buffer; //-V641 + + CALLBACK_CCID_GetSlotStatus( + requestSlotStatus->bSlot, requestSlotStatus->bSeq, responseSlotStatus); + + ccid_send_response( + furi_hal_usb_ccid->send_buffer, sizeof(struct rdr_to_pc_slot_status)); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + + } else if(message->bMessageType == PC_TO_RDR_XFRBLOCK) { + struct pc_to_rdr_xfr_block* receivedXfrBlock = + (struct pc_to_rdr_xfr_block*)message; + struct rdr_to_pc_data_block* responseDataBlock = + (struct rdr_to_pc_data_block*)&furi_hal_usb_ccid->send_buffer; + + if(furi_hal_usb_ccid->receive_buffer_data_index >= + sizeof(struct pc_to_rdr_xfr_block) + receivedXfrBlock->dwLength) { + CALLBACK_CCID_XfrBlock(receivedXfrBlock, responseDataBlock); + + ccid_send_response( + furi_hal_usb_ccid->send_buffer, + sizeof(struct rdr_to_pc_data_block) + + (sizeof(uint8_t) * responseDataBlock->dwLength)); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + } + + } else if(message->bMessageType == PC_TO_RDR_SETPARAMETERS) { + struct pc_to_rdr_set_parameters_t0* requestSetParametersT0 = + (struct pc_to_rdr_set_parameters_t0*)message; //-V641 + struct rdr_to_pc_parameters_t0* responseSetParametersT0 = + (struct rdr_to_pc_parameters_t0*)&furi_hal_usb_ccid->send_buffer; //-V641 + + CALLBACK_CCID_SetParametersT0(requestSetParametersT0, responseSetParametersT0); + + ccid_send_response( + furi_hal_usb_ccid->send_buffer, sizeof(struct rdr_to_pc_parameters_t0)); + + furi_hal_usb_ccid->receive_buffer_data_index = 0; + } + } else if(flags & WorkerEvtStop) { + break; } } + return 0; } /* Configure endpoints */ diff --git a/targets/furi_hal_include/furi_hal_usb_ccid.h b/targets/furi_hal_include/furi_hal_usb_ccid.h index 223f1623115..fbe69ce3cbd 100644 --- a/targets/furi_hal_include/furi_hal_usb_ccid.h +++ b/targets/furi_hal_include/furi_hal_usb_ccid.h @@ -1,9 +1,11 @@ #pragma once + #include "hid_usage_desktop.h" #include "hid_usage_button.h" #include "hid_usage_keyboard.h" #include "hid_usage_consumer.h" #include "hid_usage_led.h" +#include #define CCID_SHORT_APDU_SIZE (0xFF) @@ -28,10 +30,18 @@ typedef struct { void* context); } CcidCallbacks; -void furi_hal_ccid_set_callbacks(CcidCallbacks* cb, void* context); +/** Set CCID callbacks + * + * @param cb CcidCallbacks instance + * @param context The context for callbacks + */ +void furi_hal_usb_ccid_set_callbacks(CcidCallbacks* cb, void* context); + +/** Insert Smart Card */ +void furi_hal_usb_ccid_insert_smartcard(void); -void furi_hal_ccid_ccid_insert_smartcard(void); -void furi_hal_ccid_ccid_remove_smartcard(void); +/** Remove Smart Card */ +void furi_hal_usb_ccid_remove_smartcard(void); #ifdef __cplusplus }