Coding Contest 25 novembre 2016

From Sistemi Operativi
Jump to navigation Jump to search

Esercizio 1

scrivere un programma che passato come parametro il path di una directory (cwd se manca il paramtro) stampi il path relativo di tutti i file con nome palindromo presenti nel sottoalbero.


2720c84e673c75c20a27a07ffcd6826b31c8babc esercizio1.c Leonardo (talk) 17:23, 25 November 2016 (CET)

86aca4384a296bf12c69541fc5418fe4b6656e0d es1.c Fabio.capucci (talk) 17:30, 25 November 2016 (CET)

071fccfe63b8121f951444cb57001ccdd4ec02d0 Es1.c FilippoB (talk) 17:31, 25 November 2016 (CET)

235f2414cfe5b81973b1d388ce9431aa02b5f305 MatteoC (talk) 17:43, 25 November 2016 (CET)

168d3422b92fc78519e19d6a8e156b260a7798a6 testdir.c Tamino (talk) 18:06, 25 November 2016 (CET)

Esercizio 2

lancia tutti gli eseguibili della directory passata come primo paramtro e concatena gli output. (i parametri rimanenti devono essere passati a tutti gli eseguibili)

lanciatutti dir 1 2 3

se nella directory dir sono presenti a, b e c (eseguibili) lancia a 1 2 3', b 1 2 3, c 1 2 3

Esercizio 3

Scrivere un programma che deve ottenere il pid passato come parametro. indicare se e' impossibile

fdf7b609e470c43a32a50801e76e78c32aebfbb1 main.tar.gz Alexp (talk) 17:22, 25 November 2016 (CET)

In seguito il codice dell'esercizio --Alexp (talk) 13:50, 8 December 2016 (CET) :

#include <unistd.h>
#include <stdio.h>
#include <signal.h>
#include <errno.h>
#include <sys/wait.h>

#define PID 6300

void do_something(){
    //print something
    printf("---doing something---\n");
}

int main(int argc, char* argv[]) {
    int sPID = PID;
    if (argc > 1) {
        sPID = atoi(argv[1]);
    }
    pid_t pid;
    if (getpid() == sPID) {
        //if sPID matched
        printf("GOT PID (%d)!\n", sPID);
        //do something
        do_something();
    } else {
        if (kill(sPID, 0) != 0 && errno == ESRCH) {
            //while generated child has wrong sPID
            while ((pid = fork()) != sPID) {
                //if child
                if (pid == 0) {
                    if (getpid() == sPID) {
                        printf("GOT PID (%d)!\n", sPID);
                        //do something
                        do_something();
                    }
                    break;
                }
                    //if parent and error occoured
                else if (pid == -1) {
                    printf("Error: process table is full.\n");
                    break;
                }
                    //if parent and no error occoured
                else {
                    //wait for child process to finish
                    wait(NULL);
                }
            }
            //we must wait for the last child
            if (pid == sPID) {
                printf("Waiting for the last child.");
                wait(NULL);
            }
        } else {
            printf("Impossible to get pid %d(another process has it).\n", sPID);
        }
    }
    return 0;
}

Esercizio 4

Trovare i file di contenuto uguale nella directory corrente e convertirli in link dello stesso file.

Esempio di soluzione dell'esercizio Renzo (talk) 09:06, 6 December 2016 (CET). (in aula sembrava avere un bug ma non era vero. Alcuni file in /tmp non sono stati convertiti in link perché appartenevano ad altro utente).

#include <stdio.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>
#include <stdarg.h>
#include <string.h>
#include <libgen.h>
#include <errno.h>
#include <dirent.h>
#include <mhash.h>
#include <sys/types.h>
#include <sys/stat.h>

struct file {
  struct file *next;
  unsigned char hash[20];
  char *name;
};

struct file *head;

static int ckcontents(int fd1, int fd2) {
  char buf1[BUFSIZ],buf2[BUFSIZ];
  ssize_t n1, n2;
  do {
    n1 = read(fd1, buf1, BUFSIZ);
    n2 = read(fd2, buf2, BUFSIZ);
  } while (n1 == n2 && n1 > 0 && memcmp(buf1, buf2, n2 == 0));
  return n1 == n2;
}

static int cksize(int fd1, int fd2) {
  struct stat st1, st2;
  return
    fstat(fd1, &st1) == 0 &&
    fstat(fd2, &st2) == 0 &&
    st1.st_size == st2.st_size;
}

int filecmp(char *path1, char *path2) {
  int fd1 = open(path1, O_RDONLY);
  int fd2 = open(path2, O_RDONLY);
  int rval =
    fd1 >= 0 && fd2 >=0 && cksize(fd1, fd2) && ckcontents(fd1, fd2);
  close(fd1);
  close(fd2);
  return rval;
}

#if 0
void printhash(unsigned char * hash) {
  int i;
  for (i = 0; i < mhash_get_block_size(MHASH_SHA1); i++) 
    printf("%.2x", hash[i]);
}
#endif

void compute_sha1sum(char *path, char *hash) {
  int fd;
  MHASH td;
  if ((fd = open(path, O_RDONLY)) >= 0) {
    if ((td = mhash_init(MHASH_SHA1)) != MHASH_FAILED) {
      ssize_t n;
      char buf[BUFSIZ];
      while ((n = read(fd, buf, BUFSIZ)) > 0)
        mhash(td, buf, n);
      mhash_deinit(td, hash);
    }
    close(fd);
  }
}

static void check_n_link(char *name) {
  struct file **scan;
  unsigned char hash[20];
  compute_sha1sum(name, hash);
  for (scan = &head; *scan != NULL; scan = &((*scan) -> next)) {
    //printhash((*scan)->hash); printf(" - "); printhash(hash); printf("\n");
    if (memcmp((*scan)->hash, hash, 20) == 0 &&
        filecmp((*scan)->name, name)) {
      unlink(name);
      link((*scan)->name, name);
      printf("%s and %s have the same contents\n", (*scan)->name, name);
      return;
    }
  }
  *scan = malloc(sizeof(struct file));
  if (*scan) {
    (*scan)->next = NULL;
    memcpy((*scan)->hash, hash, 20);
    (*scan)->name = name;
    //printf("%s\n",name);
  }
}

static void freefilelist() {
  while (head) {
    struct file *delenda;
    delenda = head;
    head = head->next;
    free(delenda);
  }
}

void err_exit(char *fmt, ...) {
  va_list ap;

  va_start(ap, fmt);
  vfprintf(stderr, fmt, ap);
  va_end(ap);
  exit(2);
}

static int regular_only(const struct dirent *d) {
  const char *name = d->d_name;
  struct stat st;
  return stat(name, &st) == 0 && S_ISREG(st.st_mode);
}

int main(int argc, char *argv[]) {
  struct dirent **list;
  int n;
  int i;
  n = scandir(".", &list, regular_only, alphasort);
  if (n > 0) {
    for (i=0; i<n; i++) {
      char *name = list[i]->d_name;
      check_n_link(name);
    }
    freefilelist();
    for (i=0; i<n; i++)
      free(list[i]);
    free(list);
  }
}