Advertisement
Vladislav8653

7.2

Dec 19th, 2023 (edited)
666
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 4.54 KB | None | 0 0
  1. #include <unistd.h>
  2. #include <sys/types.h>
  3. #include <sys/stat.h>
  4. #include <fcntl.h>
  5. #include <dirent.h>
  6. #include <stdlib.h>
  7. #include <stdio.h>
  8. #include <string.h>
  9. #include <pthread.h>
  10.  
  11. #define MAX_PATH_LENGTH 4096
  12. #define MAX_FILENAME_LENGTH 256
  13. #define MAX_CHILD_PROCESSES 10
  14.  
  15. typedef struct {
  16.     char filename[MAX_FILENAME_LENGTH];
  17.     off_t size;
  18.     const char *destPath;  // Добавлено поле для хранения destPath
  19. } FileInfo;
  20.  
  21. int compareBySize(const void *a, const void *b) {
  22.     return ((FileInfo *)a)->size - ((FileInfo *)b)->size;
  23. }
  24.  
  25. int compareByName(const void *a, const void *b) {
  26.     return strcmp(((FileInfo *)a)->filename, ((FileInfo *)b)->filename);
  27. }
  28.  
  29. void copyFile(const char *sourcePath, const char *destPath) {
  30.     int sourceFile = open(sourcePath, O_RDONLY);
  31.     int destFile = open(destPath, O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
  32.  
  33.     char buffer[4096];
  34.     ssize_t bytesRead, bytesWritten;
  35.  
  36.     while ((bytesRead = read(sourceFile, buffer, sizeof(buffer))) > 0) {
  37.         bytesWritten = write(destFile, buffer, bytesRead);
  38.         if (bytesWritten != bytesRead) {
  39.             perror("Write error");
  40.             exit(EXIT_FAILURE);
  41.         }
  42.     }
  43.  
  44.     close(sourceFile);
  45.     close(destFile);
  46. }
  47.  
  48. void *threadFunction(void *arg) {
  49.     FileInfo *fileInfo = (FileInfo *)arg;
  50.  
  51.     printf("Thread ID: %lu, Filename: %s, Size: %ld bytes\n", pthread_self(), fileInfo->filename, (long)fileInfo->size);
  52.  
  53.     // Construct destination file path
  54.     char destFilePath[MAX_PATH_LENGTH];
  55.     snprintf(destFilePath, sizeof(destFilePath), "%s/%s", fileInfo->destPath, fileInfo->filename);
  56.  
  57.     copyFile(fileInfo->filename, destFilePath);
  58.  
  59.     return NULL;
  60. }
  61.  
  62. void sortAndCopyFiles(const char *dirPath, int sortBy, const char *destPath, int maxThreads) {
  63.     DIR *dir = opendir(dirPath);
  64.     if (dir == NULL) {
  65.         perror("Error opening directory");
  66.         exit(EXIT_FAILURE);
  67.     }
  68.  
  69.     struct dirent *entry;
  70.     struct stat fileInfo;
  71.  
  72.     int numThreads = 0;
  73.     int numFiles = 0;
  74.     FileInfo *files = malloc(MAX_CHILD_PROCESSES * sizeof(FileInfo));
  75.  
  76.     while ((entry = readdir(dir)) != NULL) {
  77.         if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0)
  78.             continue;
  79.  
  80.         char filePath[MAX_PATH_LENGTH];
  81.         snprintf(filePath, sizeof(filePath), "%s/%s", dirPath, entry->d_name);
  82.  
  83.         if (lstat(filePath, &fileInfo) == -1) {
  84.             perror("Error getting file info");
  85.             exit(EXIT_FAILURE);
  86.         }
  87.  
  88.         if (S_ISREG(fileInfo.st_mode)) {
  89.             strncpy(files[numFiles].filename, entry->d_name, MAX_FILENAME_LENGTH - 1);
  90.             files[numFiles].size = fileInfo.st_size;
  91.             files[numFiles].destPath = destPath;  // Передаем destPath в структуру FileInfo
  92.             numFiles++;
  93.  
  94.             if (numFiles >= MAX_CHILD_PROCESSES) {
  95.                 qsort(files, numFiles, sizeof(FileInfo), (sortBy == 1) ? compareBySize : compareByName);
  96.  
  97.                 for (int i = 0; i < numFiles; i++) {
  98.                     pthread_t thread;
  99.                     if (pthread_create(&thread, NULL, threadFunction, &files[i]) != 0) {
  100.                         perror("Error creating thread");
  101.                         exit(EXIT_FAILURE);
  102.                     }
  103.  
  104.                     if (pthread_join(thread, NULL) != 0) {
  105.                         perror("Error joining thread");
  106.                         exit(EXIT_FAILURE);
  107.                     }
  108.  
  109.                     numThreads++;
  110.                     if (numThreads >= maxThreads) {
  111.                         usleep(1000);  // Sleep for 1 millisecond to allow threads to finish
  112.                         numThreads--;
  113.                     }
  114.                 }
  115.  
  116.                 numFiles = 0;
  117.             }
  118.         }
  119.     }
  120.  
  121.     closedir(dir);
  122.     free(files);
  123. }
  124.  
  125. int main(int argc, char *argv[]) {
  126.     if (argc != 4) {
  127.         fprintf(stderr, "Usage: %s <source_directory> <sort_criteria> <destination_directory>\n", argv[0]);
  128.         exit(EXIT_FAILURE);
  129.     }
  130.  
  131.     const char *dirPath = argv[1];
  132.     int sortBy = atoi(argv[2]);
  133.     const char *destPath = argv[3];
  134.  
  135.     if (sortBy != 1 && sortBy != 2) {
  136.         fprintf(stderr, "Invalid sort criteria. Use 1 for sorting by size or 2 for sorting by name.\n");
  137.         exit(EXIT_FAILURE);
  138.     }
  139.  
  140.     int maxThreads;
  141.     printf("Enter the maximum number of threads: ");
  142.     scanf("%d", &maxThreads);
  143.  
  144.     sortAndCopyFiles(dirPath, sortBy, destPath, maxThreads);
  145.  
  146.     return 0;
  147. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement