לדלג לתוכן

5.9 מערכת הקבצים proc פתרון

פתרונות

פתרון 1

#include <stdio.h>
#include <string.h>

int main() {
    FILE *f = fopen("/proc/self/status", "r");
    if (f == NULL) {
        perror("fopen");
        return 1;
    }

    char line[256];
    while (fgets(line, sizeof(line), f)) {
        if (strncmp(line, "Name:", 5) == 0 ||
            strncmp(line, "Pid:", 4) == 0 ||
            strncmp(line, "PPid:", 5) == 0 ||
            strncmp(line, "VmSize:", 7) == 0) {
            printf("%s", line);
        }
    }

    fclose(f);
    return 0;
}

פלט לדוגמה:

Name:   solution1
Pid:    12345
PPid:   1000
VmSize:    5120 kB

פתרון 2

#include <stdio.h>
#include <string.h>

int main() {
    FILE *f = fopen("/proc/self/maps", "r");
    if (f == NULL) {
        perror("fopen");
        return 1;
    }

    char line[512];
    printf("אזורי זיכרון עם הרשאת הרצה:\n");
    printf("-------------------------------------------\n");

    while (fgets(line, sizeof(line), f)) {
        /*
         * פורמט השורה:
         * address           perms  offset  dev   inode  pathname
         * 55a3c8a01000-55a3c8a05000 r-xp 00001000 08:01 1234567 /usr/bin/cat
         *
         * ההרשאות מתחילות אחרי הרווח הראשון.
         * נחפש את התו 'x' בעמודת ההרשאות.
         */
        char *perms = strchr(line, ' ');
        if (perms == NULL) {
            continue;
        }
        perms++; /* מדלגים על הרווח */

        /* ההרשאות הן 4 תווים: rwxp/rwxs */
        if (strlen(perms) >= 4 && perms[2] == 'x') {
            printf("%s", line);
        }
    }

    fclose(f);
    return 0;
}

פתרון 3

#include <stdio.h>
#include <dirent.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>

int main() {
    /* פותחים 3 קבצים */
    int fd1 = open("/etc/hostname", O_RDONLY);
    int fd2 = open("/etc/passwd", O_RDONLY);
    int fd3 = open("/etc/os-release", O_RDONLY);

    if (fd1 == -1 || fd2 == -1 || fd3 == -1) {
        perror("open");
        return 1;
    }

    printf("fd-ים שנפתחו: %d, %d, %d\n\n", fd1, fd2, fd3);

    /* קוראים את /proc/self/fd/ */
    DIR *dir = opendir("/proc/self/fd");
    if (dir == NULL) {
        perror("opendir");
        return 1;
    }

    struct dirent *entry;
    while ((entry = readdir(dir)) != NULL) {
        /* מדלגים על . ו- .. */
        if (entry->d_name[0] == '.') {
            continue;
        }

        char link_path[512];
        char target[512];
        snprintf(link_path, sizeof(link_path), "/proc/self/fd/%s", entry->d_name);

        ssize_t len = readlink(link_path, target, sizeof(target) - 1);
        if (len != -1) {
            target[len] = '\0';
            printf("fd %s -> %s\n", entry->d_name, target);
        }
    }

    closedir(dir);
    close(fd1);
    close(fd2);
    close(fd3);
    return 0;
}

פלט לדוגמה:

fd-ים שנפתחו: 3, 4, 5

fd 0 -> /dev/pts/0
fd 1 -> /dev/pts/0
fd 2 -> /dev/pts/0
fd 3 -> /etc/hostname
fd 4 -> /etc/passwd
fd 5 -> /etc/os-release
fd 6 -> /proc/12345/fd

פתרון 4

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(int argc, char *argv[]) {
    if (argc != 2) {
        printf("שימוש: %s <pid>\n", argv[0]);
        return 1;
    }

    char path[256];

    /* קריאת status */
    snprintf(path, sizeof(path), "/proc/%s/status", argv[1]);
    FILE *f = fopen(path, "r");
    if (f == NULL) {
        printf("לא ניתן לפתוח %s - ודאו שהPID קיים\n", path);
        return 1;
    }

    char line[256];
    printf("=== סטטוס התהליך ===\n");
    while (fgets(line, sizeof(line), f)) {
        if (strncmp(line, "Name:", 5) == 0 ||
            strncmp(line, "State:", 6) == 0 ||
            strncmp(line, "VmSize:", 7) == 0) {
            printf("%s", line);
        }
    }
    fclose(f);

    /* קריאת cmdline */
    snprintf(path, sizeof(path), "/proc/%s/cmdline", argv[1]);
    f = fopen(path, "r");
    if (f == NULL) {
        printf("לא ניתן לפתוח %s\n", path);
        return 1;
    }

    char cmdline[4096];
    size_t bytes_read = fread(cmdline, 1, sizeof(cmdline) - 1, f);
    fclose(f);

    if (bytes_read > 0) {
        /* מחליפים את תווי ה-null ברווחים */
        for (size_t i = 0; i < bytes_read - 1; i++) {
            if (cmdline[i] == '\0') {
                cmdline[i] = ' ';
            }
        }
        cmdline[bytes_read] = '\0';
        printf("\n=== שורת הפקודה ===\n");
        printf("%s\n", cmdline);
    }

    return 0;
}

שימוש:

./solution4 1234

פלט לדוגמה:

=== סטטוס התהליך ===
Name:   bash
State:  S (sleeping)
VmSize:    10240 kB

=== שורת הפקודה ===
/bin/bash

פתרון 5

#include <stdio.h>
#include <string.h>

int main() {
    FILE *f = fopen("/proc/cpuinfo", "r");
    if (f == NULL) {
        perror("fopen");
        return 1;
    }

    char line[256];
    int core_count = 0;
    int model_printed = 0;

    while (fgets(line, sizeof(line), f)) {
        /* סופרים כמה פעמים מופיע processor */
        if (strncmp(line, "processor", 9) == 0) {
            core_count++;
        }

        /* מדפיסים את שם הדגם פעם אחת בלבד */
        if (strncmp(line, "model name", 10) == 0 && !model_printed) {
            /* מחפשים את התו : כדי להדפיס רק את הערך */
            char *value = strchr(line, ':');
            if (value != NULL) {
                value += 2; /* מדלגים על ": " */
                printf("דגם המעבד: %s", value);
            }
            model_printed = 1;
        }
    }

    printf("מספר ליבות: %d\n", core_count);

    fclose(f);
    return 0;
}

פלט לדוגמה:

דגם המעבד: Intel(R) Core(TM) i7-10700 CPU @ 2.90GHz
מספר ליבות: 8