From 2c10477a07c6e893c05c48272d344b47c8e5db60 Mon Sep 17 00:00:00 2001 From: =?utf8?q?=E8=AB=8F=E8=A8=AA=E5=AD=90?= Date: Sat, 14 Sep 2024 00:23:13 +0900 Subject: [PATCH] =?utf8?q?=E3=83=91=E3=82=B9=E3=83=AF=E3=83=BC=E3=83=89?= =?utf8?q?=E3=81=AE=E6=A4=9C=E7=B4=A2=20#14?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit --- main.c | 8 ++++- src/common.c | 76 +++++++++++++++++++++++++++++++++++++++++ src/common.h | 18 ++++++++++ src/findpass.c | 93 ++++++++++++++++++++++++++++++++++++++++++++++++++ src/findpass.h | 9 +++++ 5 files changed, 203 insertions(+), 1 deletion(-) create mode 100644 src/findpass.c create mode 100644 src/findpass.h diff --git a/main.c b/main.c index b8972b2..ca5bf13 100644 --- a/main.c +++ b/main.c @@ -7,12 +7,13 @@ #include "src/delpass.h" #include "src/genpass.h" #include "src/otppass.h" +#include "src/findpass.h" const char *sofname = "sp"; const char *version = "1.4.0"; void usage() { - printf("%s-%s\nusage: %s [-adegilosvy]\n", sofname, version, sofname); + printf("%s-%s\nusage: %s [-adefgilosvy]\n", sofname, version, sofname); } char *getfullpath(char *arg) { @@ -98,6 +99,11 @@ int main(int argc, char *argv[]) { if (fullPath == NULL) return -1; otppass(fullPath); free(fullPath); + } else if (strcmp(argv[1], "-f") == 0) { + char *fullPath = getfullpath(NULL); + if (fullPath == NULL) return -1; + findpass(fullPath, argv[2]); + free(fullPath); } else { usage(); return 1; diff --git a/src/common.c b/src/common.c index 193dcff..cd76fb8 100644 --- a/src/common.c +++ b/src/common.c @@ -1,4 +1,5 @@ #include "common.h" +#include char *getlang() { char *lang = NULL; @@ -35,3 +36,78 @@ int mkdir_r(const char *path, mode_t mode) { return 0; } + +void initList(List *list) { + list->head = NULL; + list->tail = NULL; + list->size = 0; +} + +void addElement(List *list, const char *data) { + Node *newNode = (Node *)malloc(sizeof(Node)); + if (!newNode) { + return; + } + + newNode->data = strdup(data); + newNode->next = NULL; + + if (list->tail) { + list->tail->next = newNode; + } else { + list->head = newNode; + } + + list->tail = newNode; + list->size++; +} + +char *getElement(List *list, size_t idx) { + if (idx >= list->size) return NULL; + + Node *current = list->head; + for (size_t i = 0; i < idx; i++) + current = current->next; + + return current->data; +} + +void rmElement(List *list, size_t idx) { + if (idx >= list->size) return; + + Node *current = list->head; + Node *previous = NULL; + + if (idx == 0) { + list->head = current->next; + if (list->size == 1) list->tail = NULL; + } else { + for (size_t i = 0; i < idx; i++) { + previous = current; + current = current->next; + } + previous->next = current->next; + if (idx == list->size - 1) { + list->tail = previous; + } + } + + free(current->data); + free(current); + list->size--; +} + +void freeList(List *list) { + Node *current = list->head; + + while (current) { + Node *next = current->next; + free(current->data); + free(current); + current = next; + } + + list->head = NULL; + list->tail = NULL; + list->size = 0; +} diff --git a/src/common.h b/src/common.h index 25f8f28..c8b74dd 100644 --- a/src/common.h +++ b/src/common.h @@ -10,7 +10,25 @@ #include +typedef struct Node { + char *data; + struct Node *next; +} Node; + +typedef struct { + Node *head; + Node *tail; + size_t size; +} List; + char *getlang(); int mkdir_r(const char *path, mode_t mode); +// C言語のvector +void initList(List *list); +void addElement(List *list, const char *data); +char *getElement(List *list, size_t idx); +void rmElement(List *list, size_t idx); +void freeList(List *list); + #endif diff --git a/src/findpass.c b/src/findpass.c new file mode 100644 index 0000000..fdf0a7c --- /dev/null +++ b/src/findpass.c @@ -0,0 +1,93 @@ +#include "common.h" +#include "findpass.h" + +#include +#include +#include +#include +#include + +#define MAXFINDLEN 1024 + +List fullpaths; +List dispaths; + +#if defined(__linux__) +char *strcasestr(const char *haystack, const char *needle) { + size_t needle_len = strlen(needle); + if (needle_len == 0) { + return (char *)haystack; + } + + while (*haystack) { + if (strncasecmp(haystack, needle, needle_len) == 0) { + return (char *)haystack; + } + haystack++; + } + return NULL; +} +#endif + +void rmext(char *filename) { + char *ext = strrchr(filename, '.'); + if (ext != NULL && strcmp(ext, ".gpg") == 0) { + *ext = '\0'; + } +} + +void scanDir(const char *dpath, const char *rpath, List *fpaths) { + char *lang = getlang(); + + DIR *dir = opendir(dpath); + if (!dir) { + if (strncmp(lang, "en", 2) == 0) + perror("Could not open directory"); + else perror("ディレクトリを開けられません"); + exit(EXIT_FAILURE); + } + + struct dirent *entry; + while ((entry = readdir(dir)) != NULL) { + const char *name = entry->d_name; + if (strncmp(name, ".", 1) == 0 || strncmp(name, "..", 2) == 0) continue; + + char fpath[MAXFINDLEN]; + snprintf(fpath, sizeof(fpath), "%s/%s", dpath, name); + + struct stat s; + if (stat(fpath, &s) != 0) { + closedir(dir); + return; + } + + if (S_ISDIR(s.st_mode)) { + scanDir(fpath, rpath, fpaths); + } else if (strstr(name, ".gpg") != NULL) { + const char *rel = fpath + strlen(rpath) + 1; + addElement(fpaths, rel); + addElement(&fullpaths, fpath); + char *disname = strdup(rel); + rmext(disname); + addElement(&dispaths, disname); + } + } + + closedir(dir); +} + +void findpass(const char *dpath, const char *txt) { + List fpaths; + initList(&fpaths); + initList(&fullpaths); + initList(&dispaths); + scanDir(dpath, dpath, &fpaths); + + for (size_t i = 0; i < dispaths.size; i++) { + if (strcasestr(getElement(&dispaths, i), txt) != NULL) { + printf("%s\n", getElement(&dispaths, i)); + } + } + + freeList(&fpaths); +} diff --git a/src/findpass.h b/src/findpass.h new file mode 100644 index 0000000..7a34761 --- /dev/null +++ b/src/findpass.h @@ -0,0 +1,9 @@ +#ifndef FINDPASS_H +#define FINDPASS_H + +#include "common.h" + +void scanDir(const char *dpath, const char *rpath, List *fpaths); +void findpass(const char *dpath, const char *txt); + +#endif -- 2.43.0