Files
progettoso/lib/threadpool/apiFile.c

230 lines
6.6 KiB
C
Raw Normal View History

2022-03-18 20:49:28 +01:00
#include <apiFile.h>
2022-03-31 22:26:44 +02:00
#include <taglialegna.h>
#define MAXLENMESS 512
#define MEOK "20" //OK
#define MEHE "21" // help message
// #define ME "22" // not used
#define MEFP "25" // file purged
// #define ME "40" // not used
// #define ME "41" // not used
#define MESD "42" // shutting down
#define MENT "45" // requested file action not taken
#define MESY "50" // syntax error
// #define ME "51" // not used
// #define ME "52" // not used
#define MESE "55" // server error
void openFile(char *filepath, int flags, queueT *q, long fd_c, taglia_t *taglia) {
// messaggio da scrivere sul logfile
char tmp_buf[2048];
int n = 0;
size_t m = sizeof(tmp_buf);
if(!filepath || !q || !taglia) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminata con errore\n", fd_c, flags, filepath);
errno = EINVAL;
serror(MESY, fd_c, taglia, tmp_buf);
return;
}
int found = searchFile(q, filepath); // cerco il file nella queue
int create = flags & 0x1; // also %2
int lock = flags >> 1 & 0x1; // also >>1%2
fileT *removed = NULL; // file che è stato rimosso
if(found && create) { // si vuole creare il file ma esiste già
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminata con errore\n", fd_c, flags, filepath);
errno = EEXIST;
serror(MENT, fd_c, taglia, tmp_buf);
return;
}
if(!found && !create) { // si vuole aprire e non creare un file inesistente
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore\n", fd_c, flags, filepath);
errno = ENOENT;
serror(MENT, fd_c, taglia, tmp_buf);
return;
}
if(found && !create) {
if(openFileInQueue(q, file, lock, fd_c) == -1) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore\n", fd_c, flags, filepath);
perror("openFileInQueue");
serror(MESE, fd_c, taglia, tmp_buf);
return;
}
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminata con successo\n", fd_c, flags, filepath);
sendMessage(MEOK, fd_c, taglia, tmp_buf);
return;
}
if(!found && create) { // not found and creating new file
if(getLen(q) == queue->maxLen) { // capacity miss
removed = dequeue(q);
if(!removed) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore\n", fd_c, flags, filepath);
perror("dequeue");
serror(MESE, fd_c, taglia, tmp_buf);
return;
}
fileT *f = createFileT(filepath, lock, fd_c, 1); // create new file
if(!f) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore del server\n", fd_c, flags, filepath);
perror("createFileT");
serror(MESE, fd_c, taglia);
return;
}
if(enqueue(q, f) != 0) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore del server\n", fd_c, flags, filepath);
perror("enqueue");
serror(MESE, fd_c, taglia);
return;
}
taglia_update(taglia, q, 1); // removed only one file
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" ha causato una capacity miss. File espulso \"%s\"\n", fd_c, flags, filepath, removed->filepath);
sendMessageFile(MEFP, removed, fd_c, taglia, tmp_buf);
free(removed);
return;
}
fileT *f = createFileT(filepath, lock, fd_c, 1);
if(!f) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore del server\n", fd_c, flags, filepath);
perror("createFileT");
serror(MESE, fd_c, taglia);
return;
}
if(enqueue(q, f) != 0) {
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con errore del server\n", fd_c, flags, filepath);
perror("enqueue");
serror(MESE, fd_c, taglia);
return;
}
// abbiamo aggiunto un file quindi il numero di file è cambiato
// quindi bisogna fare un update del log
taglia_update(taglia, q, 0);
n += snprintf(tmp_buf+n, m-n, "Client %ld ha richiesto una openFile (flags = %x) sul file \"%s\" e' terminato con successo\n", fd_c, flags, filepath);
sendMessage(MEOK, fd_c, taglia, tmp_buf);
return;
}
}
// invio il messaggio al client
void sendMessage(char *m, long fd_c, taglia_t *taglia, char *mlog) {
if(!m) {
m = MEOK;
}
if(writen(fd_c, m, strnlen(m, MAXLENMESS)+1) < 0) {
perror("writen");
goto _sendM_cleanup;
}
if(taglia_write(taglia, mlog) < 0)
goto _sendM_cleanup;
return;
_sendM_cleanup:
return;
}
// invio il messaggio al client e poi il file
void sendMessageFile(char *m, fileT *f, long fd_c, taglia_t *taglia, char *mlog) {
if(!f) {
errno = EINVAL;
serror(MESY, fd_c);
goto _sendMF_cleanup;
}
if(!m) {
m = MEPF;
}
if(writen(fd_c, m, strnlen(m, MAXLENMESS)+1) < 0) {
perror("writen");
goto _sendMF_cleanup;
}
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
if(sendFile(f, fd_c, taglia) < 0) {
perror("sendFile");
goto _sendMF_cleanup;
}
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
if(taglia_write(taglia, mlog) < 0)
goto _sendMF_cleanup;
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
return;
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
_sendMF_cleanup:
return;
}
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
// invio il messaggio al client e poi l'errno
void serror(char *m, long fd_c, taglia_t *taglia, char *mlog) {
if(!m) {
errno = EINVAL;
m = MESY;
}
if(writen(fd_c, m, strnlen(m, MAXLENMESS)+1) < 0) {
perror("writen");
goto _serror_cleanup;
}
if(writen(fd_c, &errno, sizeof(errno)) < 0) {
perror("writen");
goto _serror_cleanup;
}
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
if(taglia_write(taglia, mlog) < 0)
goto _serror_cleanup;
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
return;
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
_serror_cleanup:
return;
}
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void readFile(char *filepath, queueT *q, long fd_c, taglia_t *taglia);
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void readNFiles(char *numStr, queueT *q, long fd_c, taglia_t *taglia);
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void writeFile(char *filepath, size_t size, queueT *q, long fd_c, taglia_t *taglia, int append);
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void lockFile(char *filepath, queueT *q, long fd_c, taglia_t *taglia, pthread_mutex_t *lock, waitingT **waiting);
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void unlockFile(char *filepath, queueT *q, long fd_c, taglia_t *taglia, pthread_mutex_t *lock, waitingT **waiting);
2022-03-18 20:49:28 +01:00
2022-03-31 22:26:44 +02:00
void closeFile(char *filepath, queueT *q, long fd_c, taglia_t *taglia, pthread_mutex_t *lock, waitingT **waiting);
void removeFile(char *filepath, queueT *q, long fd_c, taglia_t *taglia, pthread_mutex_t *lock, waitingT **waiting);
int sendFile(fileT *f, long fd_c, taglia_t *taglia);
2022-03-18 20:49:28 +01:00
int addWaiting(waitingT **waiting, char *file, int fd);
int removeFirstWaiting(waitingT **waiting, char *file);
void clearWaiting(waitingT **waiting);