Merge branch 'dev' into astra/3746-mfp-detect

This commit is contained in:
あく
2024-06-01 17:49:49 +01:00
committed by GitHub
21 changed files with 355 additions and 90 deletions

13
.clangd Normal file
View File

@@ -0,0 +1,13 @@
CompileFlags:
Add:
- -Wno-unknown-warning-option
- -Wno-format
Remove:
- -mword-relocations
---
If:
PathMatch: .*\.h
Diagnostics:
UnusedIncludes: None

3
.gitignore vendored
View File

@@ -12,6 +12,9 @@ compile_commands.json
# JetBrains IDEs
.idea/
# Sublime Text
.sublime-project.sublime-workspace
# Python VirtEnvironments
.env
.venv

21
.sublime-project vendored Normal file
View File

@@ -0,0 +1,21 @@
{
"folders":
[
{
"path": ".",
}
],
"settings": {
"LSP": {
"clangd": {
"initializationOptions": {
"clangd.compile-commands-dir": "build/latest",
"clangd.header-insertion": null,
"clangd.query-driver": "**",
"clangd.clang-tidy": true,
},
"enabled": true,
},
},
},
}

View File

@@ -19,6 +19,8 @@
"clangd.arguments": [
// We might be able to tighten this a bit more to only include the correct toolchain.
"--query-driver=**",
"--compile-commands-dir=${workspaceFolder}/build/latest"
"--compile-commands-dir=${workspaceFolder}/build/latest",
"--clang-tidy",
"--header-insertion=never"
]
}

View File

@@ -6,8 +6,9 @@
#include <gui/view_dispatcher.h>
#include <gui/modules/submenu.h>
#include <gui/gui.h>
#include "iso7816_callbacks.h"
#include "iso7816_t0_apdu.h"
#include "iso7816_atr.h"
typedef enum {
EventTypeInput,
@@ -33,38 +34,6 @@ typedef enum {
CcidTestSubmenuIndexInsertSmartcardReader
} SubmenuIndex;
void icc_power_on_callback(uint8_t* atrBuffer, uint32_t* atrlen, void* context) {
UNUSED(context);
iso7816_answer_to_reset(atrBuffer, atrlen);
}
//dataBlock points to the buffer
//dataBlockLen tells reader how nany bytes should be read
void xfr_datablock_callback(
const uint8_t* dataBlock,
uint32_t dataBlockLen,
uint8_t* responseDataBlock,
uint32_t* responseDataBlockLen,
void* context) {
UNUSED(context);
struct ISO7816_Command_APDU commandAPDU;
iso7816_read_command_apdu(&commandAPDU, dataBlock, dataBlockLen);
struct ISO7816_Response_APDU responseAPDU;
//class not supported
responseAPDU.SW1 = 0x6E;
responseAPDU.SW2 = 0x00;
iso7816_write_response_apdu(&responseAPDU, responseDataBlock, responseDataBlockLen);
}
static const CcidCallbacks ccid_cb = {
icc_power_on_callback,
xfr_datablock_callback,
};
static void ccid_test_app_render_callback(Canvas* canvas, void* ctx) {
UNUSED(ctx);
canvas_clear(canvas);
@@ -127,6 +96,86 @@ void ccid_test_app_free(CcidTestApp* app) {
free(app);
}
void ccid_icc_power_on_callback(uint8_t* atrBuffer, uint32_t* atrlen, void* context) {
UNUSED(context);
iso7816_icc_power_on_callback(atrBuffer, atrlen);
}
void ccid_xfr_datablock_callback(
const uint8_t* pcToReaderDataBlock,
uint32_t pcToReaderDataBlockLen,
uint8_t* readerToPcDataBlock,
uint32_t* readerToPcDataBlockLen,
void* context) {
UNUSED(context);
iso7816_xfr_datablock_callback(
pcToReaderDataBlock, pcToReaderDataBlockLen, readerToPcDataBlock, readerToPcDataBlockLen);
}
static const CcidCallbacks ccid_cb = {
ccid_icc_power_on_callback,
ccid_xfr_datablock_callback,
};
void iso7816_answer_to_reset(Iso7816Atr* atr) {
//minimum valid ATR: https://smartcard-atr.apdu.fr/parse?ATR=3B+00
atr->TS = 0x3B;
atr->T0 = 0x00;
}
void iso7816_process_command(
const struct ISO7816_Command_APDU* commandAPDU,
struct ISO7816_Response_APDU* responseAPDU,
const uint8_t* commandApduDataBuffer,
uint8_t commandApduDataBufferLen,
uint8_t* responseApduDataBuffer,
uint8_t* responseApduDataBufferLen) {
//example 1: sends a command with no body, receives a response with no body
//sends APDU 0x01:0x02:0x00:0x00
//receives SW1=0x90, SW2=0x00
if(commandAPDU->CLA == 0x01 && commandAPDU->INS == 0x01) {
responseAPDU->SW1 = 0x90;
responseAPDU->SW2 = 0x00;
}
//example 2: sends a command with no body, receives a response with a body with two bytes
//sends APDU 0x01:0x02:0x00:0x00
//receives 'bc' (0x62, 0x63) SW1=0x80, SW2=0x10
else if(commandAPDU->CLA == 0x01 && commandAPDU->INS == 0x02) {
responseApduDataBuffer[0] = 0x62;
responseApduDataBuffer[1] = 0x63;
*responseApduDataBufferLen = 2;
responseAPDU->SW1 = 0x90;
responseAPDU->SW2 = 0x00;
}
//example 3: ends a command with a body with two bytes, receives a response with a body with two bytes
//sends APDU 0x01:0x03:0x00:0x00:0x02:CA:FE
//receives (0xCA, 0xFE) SW1=0x90, SW2=0x02
else if(
commandAPDU->CLA == 0x01 && commandAPDU->INS == 0x03 && commandApduDataBufferLen == 2 &&
commandAPDU->Lc == 2) {
//echo command body to response body
responseApduDataBuffer[0] = commandApduDataBuffer[0];
responseApduDataBuffer[1] = commandApduDataBuffer[1];
*responseApduDataBufferLen = 2;
responseAPDU->SW1 = 0x90;
responseAPDU->SW2 = 0x00;
} else {
responseAPDU->SW1 = 0x6A;
responseAPDU->SW2 = 0x00;
}
}
static const Iso7816Callbacks iso87816_cb = {
iso7816_answer_to_reset,
iso7816_process_command,
};
int32_t ccid_test_app(void* p) {
UNUSED(p);
@@ -135,14 +184,16 @@ int32_t ccid_test_app(void* p) {
//setup CCID USB
// On linux: set VID PID using: /usr/lib/pcsc/drivers/ifd-ccid.bundle/Contents/Info.plist
app->ccid_cfg.vid = 0x1234;
app->ccid_cfg.pid = 0x5678;
app->ccid_cfg.vid = 0x076B;
app->ccid_cfg.pid = 0x3A21;
FuriHalUsbInterface* usb_mode_prev = furi_hal_usb_get_config();
furi_hal_usb_unlock();
furi_hal_ccid_set_callbacks((CcidCallbacks*)&ccid_cb);
furi_hal_ccid_set_callbacks((CcidCallbacks*)&ccid_cb, NULL);
furi_check(furi_hal_usb_set_config(&usb_ccid, &app->ccid_cfg) == true);
iso7816_set_callbacks((Iso7816Callbacks*)&iso87816_cb);
//handle button events
CcidTestAppEvent event;
while(1) {
@@ -161,7 +212,9 @@ int32_t ccid_test_app(void* p) {
//tear down USB
furi_hal_usb_set_config(usb_mode_prev, NULL);
furi_hal_ccid_set_callbacks(NULL);
furi_hal_ccid_set_callbacks(NULL, NULL);
iso7816_set_callbacks(NULL);
//teardown view
ccid_test_app_free(app);

View File

@@ -0,0 +1,9 @@
#ifndef _ISO7816_ATR_H_
#define _ISO7816_ATR_H_
typedef struct {
uint8_t TS;
uint8_t T0;
} Iso7816Atr;
#endif //_ISO7816_ATR_H_

View File

@@ -0,0 +1,76 @@
// transforms low level calls such as XFRCallback or ICC Power on to a structured one
// an application can register these calls and listen for the callbacks defined in Iso7816Callbacks
#include "iso7816_t0_apdu.h"
#include "iso7816_atr.h"
#include "iso7816_callbacks.h"
#include <stdint.h>
#include <stddef.h>
#include <furi.h>
#define ISO7816_RESPONSE_BUFFER_SIZE 255
static Iso7816Callbacks* callbacks = NULL;
void iso7816_set_callbacks(Iso7816Callbacks* cb) {
callbacks = cb;
}
void iso7816_icc_power_on_callback(uint8_t* atrBuffer, uint32_t* atrlen) {
Iso7816Atr atr;
callbacks->iso7816_answer_to_reset(&atr);
furi_assert(atr.T0 == 0x00);
uint8_t AtrBuffer[2] = {atr.TS, atr.T0};
*atrlen = 2;
memcpy(atrBuffer, AtrBuffer, sizeof(uint8_t) * (*atrlen));
}
//dataBlock points to the buffer
//dataBlockLen tells reader how nany bytes should be read
void iso7816_xfr_datablock_callback(
const uint8_t* pcToReaderDataBlock,
uint32_t pcToReaderDataBlockLen,
uint8_t* readerToPcDataBlock,
uint32_t* readerToPcDataBlockLen) {
struct ISO7816_Response_APDU responseAPDU;
uint8_t responseApduDataBuffer[ISO7816_RESPONSE_BUFFER_SIZE];
uint8_t responseApduDataBufferLen = 0;
if(callbacks != NULL) {
struct ISO7816_Command_APDU commandAPDU;
const uint8_t* commandApduDataBuffer = NULL;
uint8_t commandApduDataBufferLen = 0;
iso7816_read_command_apdu(&commandAPDU, pcToReaderDataBlock, pcToReaderDataBlockLen);
if(commandAPDU.Lc > 0) {
commandApduDataBufferLen = commandAPDU.Lc;
commandApduDataBuffer = &pcToReaderDataBlock[5];
}
callbacks->iso7816_process_command(
&commandAPDU,
&responseAPDU,
commandApduDataBuffer,
commandApduDataBufferLen,
responseApduDataBuffer,
&responseApduDataBufferLen);
} else {
//class not supported
responseAPDU.SW1 = 0x6E;
responseAPDU.SW2 = 0x00;
}
iso7816_write_response_apdu(
&responseAPDU,
readerToPcDataBlock,
readerToPcDataBlockLen,
responseApduDataBuffer,
responseApduDataBufferLen);
}

View File

@@ -0,0 +1,28 @@
#ifndef _ISO7816_CALLBACKS_H_
#define _ISO7816_CALLBACKS_H_
#include <stdint.h>
#include "iso7816_atr.h"
#include "iso7816_t0_apdu.h"
typedef struct {
void (*iso7816_answer_to_reset)(Iso7816Atr* atr);
void (*iso7816_process_command)(
const struct ISO7816_Command_APDU* command,
struct ISO7816_Response_APDU* response,
const uint8_t* commandApduDataBuffer,
uint8_t commandApduDataBufferLen,
uint8_t* responseApduDataBuffer,
uint8_t* responseApduDataBufferLen);
} Iso7816Callbacks;
void iso7816_set_callbacks(Iso7816Callbacks* cb);
void iso7816_icc_power_on_callback(uint8_t* atrBuffer, uint32_t* atrlen);
void iso7816_xfr_datablock_callback(
const uint8_t* dataBlock,
uint32_t dataBlockLen,
uint8_t* responseDataBlock,
uint32_t* responseDataBlockLen);
#endif //_ISO7816_CALLBACKS_H_

View File

@@ -4,22 +4,14 @@
#include <furi.h>
#include "iso7816_t0_apdu.h"
void iso7816_answer_to_reset(uint8_t* dataBuffer, uint32_t* atrlen) {
//minimum valid ATR: https://smartcard-atr.apdu.fr/parse?ATR=3B+00
uint8_t AtrBuffer[2] = {
0x3B, //TS (direct convention)
0x00 // T0 (Y(1): b0000, K: 0 (historical bytes))
};
*atrlen = 2;
memcpy(dataBuffer, AtrBuffer, sizeof(uint8_t) * (*atrlen));
}
//reads dataBuffer with dataLen size, translate it into a ISO7816_Command_APDU type
//extra data will be pointed to commandDataBuffer
void iso7816_read_command_apdu(
struct ISO7816_Command_APDU* command,
const uint8_t* dataBuffer,
uint32_t dataLen) {
UNUSED(dataLen);
command->CLA = dataBuffer[0];
command->INS = dataBuffer[1];
command->P1 = dataBuffer[2];
@@ -27,11 +19,30 @@ void iso7816_read_command_apdu(
command->Lc = dataBuffer[4];
}
//data buffer countains the whole APU response (response + trailer (SW1+SW2))
void iso7816_write_response_apdu(
const struct ISO7816_Response_APDU* response,
uint8_t* dataBuffer,
uint32_t* dataLen) {
dataBuffer[0] = response->SW1;
dataBuffer[1] = response->SW2;
*dataLen = 2;
uint8_t* readerToPcDataBlock,
uint32_t* readerToPcDataBlockLen,
uint8_t* responseDataBuffer,
uint32_t responseDataLen) {
uint32_t responseDataBufferIndex = 0;
//response body
if(responseDataLen > 0) {
while(responseDataBufferIndex < responseDataLen) {
readerToPcDataBlock[responseDataBufferIndex] =
responseDataBuffer[responseDataBufferIndex];
responseDataBufferIndex++;
}
}
//trailer
readerToPcDataBlock[responseDataBufferIndex] = response->SW1;
responseDataBufferIndex++;
readerToPcDataBlock[responseDataBufferIndex] = response->SW2;
responseDataBufferIndex++;
*readerToPcDataBlockLen = responseDataBufferIndex;
}

View File

@@ -2,6 +2,8 @@
#define _ISO7816_T0_APDU_H_
#include <stdint.h>
#include "iso7816_atr.h"
#include "core/common_defines.h"
struct ISO7816_Command_APDU {
//header
@@ -20,13 +22,15 @@ struct ISO7816_Response_APDU {
uint8_t SW2;
} FURI_PACKED;
void iso7816_answer_to_reset(uint8_t* atrBuffer, uint32_t* atrlen);
void iso7816_answer_to_reset(Iso7816Atr* atr);
void iso7816_read_command_apdu(
struct ISO7816_Command_APDU* command,
const uint8_t* dataBuffer,
uint32_t dataLen);
void iso7816_write_response_apdu(
const struct ISO7816_Response_APDU* response,
uint8_t* dataBuffer,
uint32_t* dataLen);
uint8_t* readerToPcDataBlock,
uint32_t* readerToPcDataBlockLen,
uint8_t* responseDataBuffer,
uint32_t responseDataLen);
#endif //_ISO7816_T0_APDU_H_

View File

@@ -80,6 +80,14 @@ SubGhzProtocolStatus subghz_txrx_gen_data_protocol_and_te(
FURI_LOG_E(TAG, "Unable to update Te");
}
}
if(ret == SubGhzProtocolStatusOk) {
uint32_t guard_time = 30;
if(!flipper_format_update_uint32(
instance->fff_data, "Guard_time", (uint32_t*)&guard_time, 1)) {
ret = SubGhzProtocolStatusErrorParserOthers;
FURI_LOG_E(TAG, "Unable to update Guard_time");
}
}
return ret;
}

View File

@@ -20,6 +20,7 @@ env = ENV.Clone(
"fbt_resources",
],
COMPILATIONDB_USE_ABSPATH=False,
COMPILATIONDB_USE_BINARY_ABSPATH=True,
BUILD_DIR=fw_build_meta["build_dir"],
IS_BASE_FIRMWARE=fw_build_meta["type"] == "firmware",
FW_FLAVOR=fw_build_meta["flavor"],

View File

@@ -13,6 +13,7 @@
*/
#define TAG "SubGhzProtocolPrinceton"
#define PRINCETON_GUARD_TIME_DEFALUT 30 //GUARD_TIME = PRINCETON_GUARD_TIME_DEFALUT * TE
static const SubGhzBlockConst subghz_protocol_princeton_const = {
.te_short = 390,
@@ -29,6 +30,7 @@ struct SubGhzProtocolDecoderPrinceton {
uint32_t te;
uint32_t last_data;
uint32_t guard_time;
};
struct SubGhzProtocolEncoderPrinceton {
@@ -38,6 +40,7 @@ struct SubGhzProtocolEncoderPrinceton {
SubGhzBlockGeneric generic;
uint32_t te;
uint32_t guard_time;
};
typedef enum {
@@ -135,8 +138,9 @@ static bool
//Send Stop bit
instance->encoder.upload[index++] = level_duration_make(true, (uint32_t)instance->te);
//Send PT_GUARD
instance->encoder.upload[index++] = level_duration_make(false, (uint32_t)instance->te * 30);
//Send PT_GUARD_TIME
instance->encoder.upload[index++] =
level_duration_make(false, (uint32_t)instance->te * instance->guard_time);
return true;
}
@@ -165,6 +169,11 @@ SubGhzProtocolStatus
break;
}
//optional parameter parameter
if(!flipper_format_read_uint32(
flipper_format, "Guard_time", (uint32_t*)&instance->guard_time, 1)) {
instance->guard_time = PRINCETON_GUARD_TIME_DEFALUT;
}
flipper_format_read_uint32(
flipper_format, "Repeat", (uint32_t*)&instance->encoder.repeat, 1);
@@ -235,6 +244,7 @@ void subghz_protocol_decoder_princeton_feed(void* context, bool level, uint32_t
instance->decoder.decode_data = 0;
instance->decoder.decode_count_bit = 0;
instance->te = 0;
instance->guard_time = PRINCETON_GUARD_TIME_DEFALUT;
}
break;
case PrincetonDecoderStepSaveDuration:
@@ -257,6 +267,7 @@ void subghz_protocol_decoder_princeton_feed(void* context, bool level, uint32_t
instance->generic.data = instance->decoder.decode_data;
instance->generic.data_count_bit = instance->decoder.decode_count_bit;
instance->guard_time = round((float)duration / instance->te);
if(instance->base.callback)
instance->base.callback(&instance->base, instance->base.context);
@@ -323,6 +334,12 @@ SubGhzProtocolStatus subghz_protocol_decoder_princeton_serialize(
FURI_LOG_E(TAG, "Unable to add TE");
ret = SubGhzProtocolStatusErrorParserTe;
}
if((ret == SubGhzProtocolStatusOk) &&
!flipper_format_write_uint32(flipper_format, "Guard_time", &instance->guard_time, 1)) {
FURI_LOG_E(TAG, "Unable to add Guard_time");
ret = SubGhzProtocolStatusErrorParserOthers;
}
return ret;
}
@@ -349,6 +366,10 @@ SubGhzProtocolStatus
ret = SubGhzProtocolStatusErrorParserTe;
break;
}
if(!flipper_format_read_uint32(
flipper_format, "Guard_time", (uint32_t*)&instance->guard_time, 1)) {
instance->guard_time = PRINCETON_GUARD_TIME_DEFALUT;
}
} while(false);
return ret;

View File

@@ -12,3 +12,4 @@ def generate(env):
env["LINK"] = env["CXX"]
env["CXX_NOCACHE"] = env["CXX"]
env["CXX"] = "$CCACHE $CXX_NOCACHE"
env.AppendUnique(COMPILATIONDB_OMIT_BINARIES=["ccache"])

View File

@@ -32,7 +32,7 @@ which is the name that most clang tools search for by default.
import fnmatch
import itertools
import json
from shlex import quote
from shlex import join, split
import SCons
from SCons.Tool.asm import ASPPSuffixes, ASSuffixes
@@ -108,6 +108,10 @@ def make_emit_compilation_DB_entry(comstr):
return emit_compilation_db_entry
def __is_value_true(value):
return value in [True, 1, "True", "true"]
def compilation_db_entry_action(target, source, env, **kw):
"""
Create a dictionary with evaluated command line, target, source
@@ -126,16 +130,19 @@ def compilation_db_entry_action(target, source, env, **kw):
env=env["__COMPILATIONDB_ENV"],
)
# We assume first non-space character is the executable
executable = command.split(" ", 1)[0]
if not (tool_path := _TOOL_PATH_CACHE.get(executable, None)):
tool_path = env.WhereIs(executable) or executable
_TOOL_PATH_CACHE[executable] = tool_path
# If there are spaces in the executable path, we need to quote it
if " " in tool_path:
tool_path = quote(tool_path)
# Replacing the executable with the full path
command = tool_path + command[len(executable) :]
cmdline = split(command)
binaries_to_omit = env["COMPILATIONDB_OMIT_BINARIES"]
while (executable := cmdline[0]) in binaries_to_omit:
cmdline.pop(0)
if __is_value_true(env["COMPILATIONDB_USE_BINARY_ABSPATH"]):
if not (tool_path := _TOOL_PATH_CACHE.get(executable, None)):
tool_path = env.WhereIs(executable) or executable
_TOOL_PATH_CACHE[executable] = tool_path
# Replacing the executable with the full path
executable = tool_path
command = join((executable, *cmdline[1:]))
entry = {
"directory": env.Dir("#").abspath,
@@ -150,7 +157,7 @@ def compilation_db_entry_action(target, source, env, **kw):
def write_compilation_db(target, source, env):
entries = []
use_abspath = env["COMPILATIONDB_USE_ABSPATH"] in [True, 1, "True", "true"]
use_abspath = __is_value_true(env["COMPILATIONDB_USE_ABSPATH"])
use_path_filter = env.subst("$COMPILATIONDB_PATH_FILTER")
use_srcpath_filter = env.subst("$COMPILATIONDB_SRCPATH_FILTER")
@@ -225,6 +232,8 @@ def generate(env, **kwargs):
COMPILATIONDB_USE_ABSPATH=False,
COMPILATIONDB_PATH_FILTER="",
COMPILATIONDB_SRCPATH_FILTER="",
COMPILATIONDB_OMIT_BINARIES=[],
COMPILATIONDB_USE_BINARY_ABSPATH=False,
)
components_by_suffix = itertools.chain(

View File

@@ -102,6 +102,7 @@ env = core_env.Clone(
core_env.subst("$SDK_DEFINITION"), load_version_only=True
).version,
APPCHECK_COMSTR="\tAPPCHK\t${SOURCE}\n\t\tTarget: ${TARGET_HW}, API: ${UFBT_API_VERSION}",
COMPILATIONDB_USE_BINARY_ABSPATH=True,
)
wrap_tempfile(env, "LINKCOM")

View File

@@ -1,5 +1,5 @@
entry,status,name,type,params
Version,+,62.3,,
Version,+,63.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,,
@@ -1157,7 +1157,7 @@ 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*
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"
1 entry status name type params
2 Version + 62.3 63.0
3 Header + applications/services/bt/bt_service/bt.h
4 Header + applications/services/bt/bt_service/bt_keys_storage.h
5 Header + applications/services/cli/cli.h
1157 Function + furi_hal_bus_reset void FuriHalBus
1158 Function + furi_hal_ccid_ccid_insert_smartcard void
1159 Function + furi_hal_ccid_ccid_remove_smartcard void
1160 Function + furi_hal_ccid_set_callbacks void CcidCallbacks* CcidCallbacks*, void*
1161 Function + furi_hal_cdc_get_ctrl_line_state uint8_t uint8_t
1162 Function + furi_hal_cdc_get_port_settings usb_cdc_line_coding* uint8_t
1163 Function + furi_hal_cdc_receive int32_t uint8_t, uint8_t*, uint16_t

View File

@@ -1,5 +1,5 @@
entry,status,name,type,params
Version,+,62.3,,
Version,+,63.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,,
@@ -1258,7 +1258,7 @@ 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*
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"
1 entry status name type params
2 Version + 62.3 63.0
3 Header + applications/drivers/subghz/cc1101_ext/cc1101_ext_interconnect.h
4 Header + applications/services/bt/bt_service/bt.h
5 Header + applications/services/bt/bt_service/bt_keys_storage.h
1258 Function + furi_hal_bus_reset void FuriHalBus
1259 Function + furi_hal_ccid_ccid_insert_smartcard void
1260 Function + furi_hal_ccid_ccid_remove_smartcard void
1261 Function + furi_hal_ccid_set_callbacks void CcidCallbacks* CcidCallbacks*, void*
1262 Function + furi_hal_cdc_get_ctrl_line_state uint8_t uint8_t
1263 Function + furi_hal_cdc_get_port_settings usb_cdc_line_coding* uint8_t
1264 Function + furi_hal_cdc_receive int32_t uint8_t, uint8_t*, uint16_t

View File

@@ -184,6 +184,7 @@ 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];
static void* ccid_set_string_descr(char* str) {
furi_check(str);
@@ -330,7 +331,9 @@ void CALLBACK_CCID_IccPowerOn(
if(smartcard_inserted) {
if(callbacks[CCID_SLOT_INDEX] != NULL) {
callbacks[CCID_SLOT_INDEX]->icc_power_on_callback(
responseDataBlock->abData, &responseDataBlock->dwLength, NULL);
responseDataBlock->abData,
&responseDataBlock->dwLength,
cb_ctx[CCID_SLOT_INDEX]);
responseDataBlock->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR |
CCID_ICCSTATUS_PRESENTANDACTIVE;
} else {
@@ -364,7 +367,7 @@ void CALLBACK_CCID_XfrBlock(
receivedXfrBlock->dwLength,
responseDataBlock->abData,
&responseDataBlock->dwLength,
NULL);
cb_ctx[CCID_SLOT_INDEX]);
responseDataBlock->bStatus = CCID_COMMANDSTATUS_PROCESSEDWITHOUTERROR |
CCID_ICCSTATUS_PRESENTANDACTIVE;
} else {
@@ -389,8 +392,9 @@ void furi_hal_ccid_ccid_remove_smartcard(void) {
smartcard_inserted = false;
}
void furi_hal_ccid_set_callbacks(CcidCallbacks* cb) {
void furi_hal_ccid_set_callbacks(CcidCallbacks* cb, void* context) {
callbacks[CCID_SLOT_INDEX] = cb;
cb_ctx[CCID_SLOT_INDEX] = context;
}
static void ccid_rx_ep_callback(usbd_device* dev, uint8_t event, uint8_t ep) {

View File

@@ -78,21 +78,21 @@ static bool flipper_update_load_stage(const FuriString* work_dir, UpdateManifest
furi_string_free(loader_img_path);
void* img = malloc(stat.fsize);
uint32_t bytes_read = 0;
uint32_t read_total = 0;
uint16_t read_current = 0;
const uint16_t MAX_READ = 0xFFFF;
uint32_t crc = 0;
do {
uint16_t size_read = 0;
if(f_read(&file, img + bytes_read, MAX_READ, &size_read) != FR_OK) { //-V769
if(f_read(&file, img + read_total, MAX_READ, &read_current) != FR_OK) { //-V769
break;
}
crc = crc32_calc_buffer(crc, img + bytes_read, size_read);
bytes_read += size_read;
} while(bytes_read == MAX_READ);
crc = crc32_calc_buffer(crc, img + read_total, read_current);
read_total += read_current;
} while(read_current == MAX_READ);
do {
if((bytes_read != stat.fsize) || (crc != manifest->staged_loader_crc)) {
if((read_total != stat.fsize) || (crc != manifest->staged_loader_crc)) {
break;
}

View File

@@ -19,14 +19,14 @@ typedef struct {
typedef struct {
void (*icc_power_on_callback)(uint8_t* dataBlock, uint32_t* dataBlockLen, void* context);
void (*xfr_datablock_callback)(
const uint8_t* dataBlock,
uint32_t dataBlockLen,
uint8_t* responseDataBlock,
uint32_t* responseDataBlockLen,
const uint8_t* pcToReaderDataBlock,
uint32_t pcToReaderDataBlockLen,
uint8_t* readerToPcDataBlock,
uint32_t* readerToPcDataBlockLen,
void* context);
} CcidCallbacks;
void furi_hal_ccid_set_callbacks(CcidCallbacks* cb);
void furi_hal_ccid_set_callbacks(CcidCallbacks* cb, void* context);
void furi_hal_ccid_ccid_insert_smartcard(void);
void furi_hal_ccid_ccid_remove_smartcard(void);