#ifndef _PARSE_MOUNT_H #define _PARSE_MOUNT_H #include typedef struct { char *opt; char *notopt; char *desc; unsigned int val; } MU_MOUNT_OPTS; MU_MOUNT_OPTS mu_options[] = { {"defaults", NULL, NULL, 0}, {"ro", "rw", "Read only / Read and write", MS_RDONLY}, {"remount", NULL, "Remount a mounted filesystem", MS_REMOUNT}, {"sync", "async", "Writes are [a]synchronous", MS_SYNCHRONOUS}, {"nodev", "dev", "(Dis)allow use of special device files", MS_NODEV}, {"bind", "rbind", "Bind a file or directory", MS_BIND}, {"noexec", "exec", "(Dis)allow use of executable files", MS_NOEXEC}, {"noatime", "atime", "Disable/enable updates to inode access times", MS_NOATIME} }; unsigned long mu_parse_opts(char *str, char *data, const size_t data_size) { memset(data, '\0', data_size); unsigned long opt = 0; size_t data_len = 0; char *token = strtok(str, ","); while (token != NULL) { int invalidopt = 1; for (size_t i = 0; i < sizeof(mu_options) / sizeof(mu_options[0]); i++) { if (mu_options[i].opt && !strcmp(token, mu_options[i].opt)) { opt |= mu_options[i].val; invalidopt = 0; break; } if (mu_options[i].notopt && !strcmp(token, mu_options[i].notopt)) { opt &= ~mu_options[i].val; invalidopt = 0; break; } } /* Unknow opt, pass in mount() */ size_t len = strlen(token); if (invalidopt && len > 0) { /* Copy token string */ for (size_t i = 0; i < len; i++) { if (data_len + 1 >= data_size) break; else { data[data_len] = token[i]; data_len++; } } if (data_len && data_len + 1 < data_size) data[data_len++] = ','; } token = strtok(NULL, ","); } if (data_len > 0) data[data_len - 1] = '\0'; return opt; } #endif