Skip to content

Commit f284e6a

Browse files
authored
Merge pull request #28 from choco-technologies/copilot/add-driver-name-support-in-sections
Support per-section driver_name in INI config files
2 parents 2183763 + 194bad3 commit f284e6a

1 file changed

Lines changed: 112 additions & 11 deletions

File tree

src/dmdevfs.c

Lines changed: 112 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,8 @@
2323
#define DMDEVFS_CONTEXT_MAGIC 0x444D4456 // 'DMDV'
2424
#define ROOT_DIRECTORY_NAME "/"
2525
#define MAX_PATH_LENGTH (DMOD_MAX_MODULE_NAME_LENGTH + 20)
26+
#define INI_LINE_BUFFER_SIZE 256
27+
#define INI_MAIN_SECTION "main"
2628

2729
/**
2830
* @brief Type definition for path strings
@@ -73,6 +75,7 @@ struct dmfsi_context
7375
// ============================================================================
7476
static int configure_drivers(dmfsi_context_t ctx, const char* driver_name, const char* config_path);
7577
static driver_node_t* configure_driver(const char* driver_name, dmini_context_t config_ctx);
78+
static int configure_section_drivers(dmfsi_context_t ctx, dmini_context_t config_ctx, const char* config_path);
7679
static int unconfigure_drivers(dmfsi_context_t ctx);
7780
static bool is_file(const char* path);
7881
static bool is_driver( const char* name);
@@ -851,19 +854,27 @@ static int configure_drivers(dmfsi_context_t ctx, const char* driver_name, const
851854
continue;
852855
}
853856

854-
driver_node_t* driver_node = configure_driver(module_name, config_ctx);
855-
dmini_destroy(config_ctx);
856-
if (driver_node == NULL)
857+
// Section-specific driver_name entries take priority over the file/directory
858+
// derived driver name. Only configure the main driver when no section-level
859+
// drivers are present in the file.
860+
int section_drivers_added = configure_section_drivers(ctx, config_ctx, full_path);
861+
if (section_drivers_added == 0)
857862
{
858-
DMOD_LOG_ERROR("Failed to configure driver: %s\n", module_name);
859-
continue;
860-
}
861-
if(!dmlist_push_back(ctx->drivers, driver_node))
862-
{
863-
DMOD_LOG_ERROR("Failed to add driver to list: %s\n", module_name);
864-
Dmod_Free(driver_node);
865-
continue;
863+
driver_node_t* driver_node = configure_driver(module_name, config_ctx);
864+
if (driver_node != NULL)
865+
{
866+
if(!dmlist_push_back(ctx->drivers, driver_node))
867+
{
868+
DMOD_LOG_ERROR("Failed to add driver to list: %s\n", module_name);
869+
Dmod_Free(driver_node);
870+
}
871+
}
872+
else
873+
{
874+
DMOD_LOG_ERROR("Failed to configure driver: %s\n", module_name);
875+
}
866876
}
877+
dmini_destroy(config_ctx);
867878
}
868879
else
869880
{
@@ -944,6 +955,96 @@ static driver_node_t* configure_driver(const char* driver_name, dmini_context_t
944955
return driver_node;
945956
}
946957

958+
/**
959+
* @brief Configure drivers for non-main sections that contain a driver_name key
960+
*
961+
* Scans the config file line by line for INI section headers. For each section
962+
* other than "main" that contains a driver_name key, a new driver is configured
963+
* with the INI context restricted to that section via dmini_set_active_section,
964+
* so the driver only sees the keys belonging to its own section.
965+
*
966+
* Returns the number of section-specific drivers that were successfully added.
967+
* A non-zero return value signals to the caller that the file is a multi-driver
968+
* config and no fallback main driver should be configured.
969+
*/
970+
static int configure_section_drivers(dmfsi_context_t ctx, dmini_context_t config_ctx, const char* config_path)
971+
{
972+
void* file = Dmod_FileOpen(config_path, "r");
973+
if (file == NULL)
974+
{
975+
DMOD_LOG_ERROR("Failed to open config file for section scan: %s\n", config_path);
976+
return 0;
977+
}
978+
979+
int num_added = 0;
980+
char line[INI_LINE_BUFFER_SIZE];
981+
while (Dmod_FileReadLine(line, sizeof(line), file) != NULL)
982+
{
983+
// Skip lines that don't start with '[' (ignore leading whitespace)
984+
char* p = line;
985+
while (*p == ' ' || *p == '\t') p++;
986+
if (*p != '[') continue;
987+
988+
// Find closing bracket
989+
char* end = strchr(p, ']');
990+
if (end == NULL || end <= p) continue;
991+
992+
// Extract section name
993+
size_t name_len = (size_t)(end - p - 1);
994+
if (name_len == 0 || name_len >= DMOD_MAX_MODULE_NAME_LENGTH) continue;
995+
996+
char section_name[DMOD_MAX_MODULE_NAME_LENGTH];
997+
strncpy(section_name, p + 1, name_len);
998+
section_name[name_len] = '\0';
999+
1000+
// Trim trailing whitespace from section name
1001+
size_t slen = strlen(section_name);
1002+
while (slen > 0 && (section_name[slen - 1] == ' ' || section_name[slen - 1] == '\t'))
1003+
{
1004+
slen--;
1005+
}
1006+
section_name[slen] = '\0';
1007+
1008+
// Skip empty section names and the "main" section (handled by existing logic)
1009+
if (slen == 0 || strcmp(section_name, INI_MAIN_SECTION) == 0) continue;
1010+
1011+
// Check if this section has a driver_name key
1012+
if (!dmini_has_key(config_ctx, section_name, "driver_name")) continue;
1013+
1014+
const char* drv_name = dmini_get_string(config_ctx, section_name, "driver_name", NULL);
1015+
if (drv_name == NULL) continue;
1016+
1017+
char module_name[DMOD_MAX_MODULE_NAME_LENGTH];
1018+
strncpy(module_name, drv_name, sizeof(module_name));
1019+
module_name[sizeof(module_name) - 1] = '\0';
1020+
1021+
// Restrict the INI context to this section and configure the driver.
1022+
// Token 0 means no owner-token protection (context was created with dmini_create).
1023+
dmini_set_active_section(config_ctx, section_name, 0);
1024+
driver_node_t* driver_node = configure_driver(module_name, config_ctx);
1025+
dmini_clear_active_section(config_ctx, 0);
1026+
1027+
if (driver_node == NULL)
1028+
{
1029+
DMOD_LOG_ERROR("Failed to configure driver for section [%s]: %s\n", section_name, module_name);
1030+
continue;
1031+
}
1032+
1033+
if (!dmlist_push_back(ctx->drivers, driver_node))
1034+
{
1035+
DMOD_LOG_ERROR("Failed to add driver to list: %s\n", module_name);
1036+
Dmod_Free(driver_node);
1037+
}
1038+
else
1039+
{
1040+
num_added++;
1041+
}
1042+
}
1043+
1044+
Dmod_FileClose(file);
1045+
return num_added;
1046+
}
1047+
9471048
/**
9481049
* @brief Unconfigure and unload all drivers
9491050
*/

0 commit comments

Comments
 (0)