/***************************************************************************** * Softwaresysteme I - Klausur vom März 2005 * * Datei: fileattrd.c * Autor: Goethe * Datum: 07.09.2005 *****************************************************************************/ #include #include #include #include #include #include #include #include #include #include #include /* Funktiondeklarationen, globale Variablen */ void serve(int); char *prattr(char*); /* Funktion main */ int main( int argc, char *argv[] ) { /* lokale Variablen und was man sonst am Anfang so vorbereitet */ int sd, cd; struct sockaddr_in sin; struct sigaction action; pid_t pid; if( argc != 2 ) { fprintf( stderr, "usage: %s \n", argv[0] ); return -1; } /* Socket öffnen */ if( (sd = socket( PF_INET, SOCK_STREAM, 0 )) == -1 ) { perror( "Fehler beim Öffnen des Socket" ); return -1; } /* Socket an angegebenen Port und beliebige IP-Adressen binden */ sin.sin_family = AF_INET; sin.sin_addr.s_addr = htonl(INADDR_ANY); sin.sin_port = htons(atoi(argv[1])); if( bind( sd, (struct sockaddr*)&sin, sizeof(sin) ) == -1 ) { perror( "Fehler beim Binden des Socket" ); return -1; } /* Warteschlange ankommender Verbindungen auf 5 einstellen */ if( listen( sd, 5 ) == -1 ) { perror( "Fehler beim Einrichten der Verbindungswarteschlange" ); return -1; } /* Signalhandler für SIGCHLD einrichten */ memset( &action, 0, sizeof(action) ); action.sa_handler = SIG_DFL; sigemptyset( &action.sa_mask ); action.sa_flags = SA_NOCLDSTOP | SA_NOCLDWAIT; if( sigaction( SIGCHLD, &action, NULL ) == -1 ) { perror( "Fehler beim Einrichten des Signalhandlers" ); return -1; } while(1) { /* Verbindung annehmen */ if( (cd = accept( sd, NULL, 0 )) == -1 ) continue; /* Prozess zur Kommandoausführung erzeugen */ pid = fork(); /* Fehler bei Prozesserzeugung */ if( pid == -1 ) { perror( "Fehler beim Erzeugen des Sohnprozesses" ); } /* Sohnprozess */ else if( pid == 0 ) { serve(cd); exit(0); } close(cd); } } /* Ende Funktion main */ /* serve Funktion */ void serve( int cd ) { char pathname[130]; char output[1024]; char *strattr; int c, i; while( (c = read( cd, pathname, 129 )) != -1 ) { pathname[c] = '\0'; for( i = strlen(pathname); i >= 0; i-- ) { if( pathname[i] == '\n' || pathname[i] == 13 ) pathname[i] = '\0'; } strattr = prattr(pathname); if( strattr == NULL ) { snprintf( output, sizeof(output), "%s: %s\n", pathname, strerror(errno) ); write( cd, output, strlen(output) ); } else { write( cd, strattr, strlen(strattr) ); free(strattr); } } } /* prattr Funktion */ char *prattr( char *filename ) { struct stat buf; char *out = (char*)malloc(1024); if( out == NULL ) return NULL; if( lstat(filename, &buf ) == -1 ) return NULL; strcpy( out, filename ); if( S_ISREG(buf.st_mode) ) sprintf( out+strlen(filename), " F %d\n", buf.st_size ); else if( S_ISDIR(buf.st_mode) ) strcat( out, " D\n" ); else strcat( out, " X\n" ); return out; }