Quel est le bug ? - C - Programmation
Marsh Posté le 29-03-2006 à 09:54:41
Flemme de lire un programme non formaté avec des smilies partout, merci d'utiliser les balises [cpp][/cpp].
Et pour le "point" supplémentaire, c'est peut-être pour désigner le répertoire courant.
Marsh Posté le 29-03-2006 à 10:39:38
il y a plein d'erreurs de syntaxe
Citation : ls.c: In function `printfile': |
Marsh Posté le 29-03-2006 à 15:03:17
mayapour a écrit : En testant ce petit programme qui est l'équivalent du ls sous linux avec différentes options, je me suis appercu qu'il affiche un . (point) en trop avant le listing. |
Pas très clair comme code...
|
Sinon, le '.' est normal. Il désigne le répertoire courant.
Marsh Posté le 29-03-2006 à 02:13:12
Bonjour,
En testant ce petit programme qui est l'équivalent du ls sous linux avec différentes options, je me suis appercu qu'il affiche un . (point) en trop avant le listing.
Quelqu'un pourait me dire pourquoi ? comment ne plus l'afficher ?
Merci par avance
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <dirent.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <pwd.h>
#include <grp.h>
#include <time.h>
#define space 100
/* Déclaration des différentes options de my_ls */
struct options{
int R; /* Affichage récursif du contenu des dossiers */
int n; /* Affichage numéric UIDs et GIDs*/
int l; /* Affichage listé en détails (droits, groupe, date, ...) */
int i; /* Affiche l'index d'entrée de chaque fichier */
int s; /* Affiche la taille de chaque fichier */
int d; /* Affichage le répertoire d'entrée seul */
int a; /* Affichage de tous les fichiers y compris les . */
};
/* Revoie la dernière composante d'un chemin
(ce qui est passé après le dernier slash, s'il y en a un) */
char *dirname(char *name){
int i=strlen(name);
while(i>=0 && name[i]!='/') i--;
return name+i+1;
}
/* Affichage du fichier selon l'option passée
Récuperation des caracteristiques des fichiers */
int printfile(char *namefile, struct options option){
struct stat s;
int i, j;
char plug[space+1];
if (lstat(namefile, &s)){
fprintf(stderr,"%s :", namefile);
perror("lstat()" );
return(2);
}
if (option.i)
printf("%7d ",(int) s.st_ino);
if (option.s)
printf("%3d ", (int)s.st_blocks);
if (option.n || option.l){
char d[]="?rwxrwxrwx";
int flag[]={S_IRUSR,S_IWUSR,S_IXUSR,S_IRGRP,S_IWGRP,S_IXGRP,S_IROTH,
S_IWOTH,S_IXOTH,S_ISUID,S_ISGID,S_ISVTX};
/* respectivement : le propriétaire a le droit de lecture, d'écriture,
d'exécution, le groupe a le droit de lecture, d'écriture, d'exécution,
les autres ont le droit de lecture, d'écriture, d'exécution,
bit Set-UID, bit Set-Gid, bit "sticky" */
switch (s.st_mode & S_IFMT){ /* & masque du type de fichier /*
case S_IFLNK: d[0]='l'; break; /* fichier lien symbolique */
case S_IFDIR: d[0]='d'; break; /* s'il s'agit d'un directory */
case S_IFREG: d[0]='-'; break; /* fichier normal */
}
for (i=0;i<9;i++)
if (!(s.st_mode & flag[i])) d[i+1]='-';
for (i=0; i<3;i++)
if ((s.st_mode & flag[9+i])) d[3*i+3]='s';
printf("%s %3d ", d, (int) s.st_nlink);
struct passwd *pwd = getpwuid(s.st_uid);
if (pwd && !option.n) printf("%8s ", pwd->pw_name);
else printf("%4d ", (int) s.st_uid);
struct group *grp = getgrgid(s.st_gid);
if (grp && !option.n) printf("%8s ", grp->gr_name);
else printf("%8d ", (int) s.st_gid);
printf("%7d ", (int) s.st_size);
printf("%.24s ", ctime(&(s.st_mtime)));
}
printf("%s", option.d?namefile:dirname(namefile));
if (S_ISLNK(s.st_mode)){
if ((j=readlink(namefile, plug, space))==-1){
perror("readlink()" );
}else{
plug[j]=0;
printf(" -> %s ", plug);
}
}
printf("\n" );
return(0);
}
/* Affichage d'un fichier ou repertoire.
Pour un fichier, on l'affiche simplement
Pour un repertoire, on fait la descente récursive si -R */
int printdirectory(char *directory, struct options option){
struct dirent **l;
struct stat s;
char list[space];
int i,j,tot=0;
printf("%s:\n", directory);
if ((i=scandir(directory, &l, NULL, alphasort))==-1){
perror("scandir()" );
return(1);
}
if (option.s || option.l){
for (j=0; j<i; j++){
if (l[j]->d_name[0] == '.' && option.a==0)
continue;
snprintf(list, space, "%s/%s",directory, l[j]->d_name);
if (lstat(list,&s)){
fprintf(stderr,"%s:", list);
perror("lstat()" );
continue;
}
tot += s.st_blocks;
}
printf("Total: %d\n", tot);
}
for (j=0;j<i;j++){
if ((l[j]->d_name)[0] == '.' && option.a==0)
continue;
snprintf(list, space, "%s/%s",directory, l[j]->d_name);
if (lstat(list,&s)){
fprintf(stderr,"%s: ", list);
perror("lstat()" );
continue;
}
printfile(list, option);
}
printf("\n" );
for (j=0; j<i; j++){
snprintf(list, space, "%s/%s",directory, l[j]->d_name);
if (lstat(list,&s)){
fprintf(stderr,"%s: ", list);
perror("lstat()" );
}else
if (S_ISDIR(s.st_mode) && strcmp(l[j]->d_name,"." )
&& strcmp(l[j]->d_name,".." ) && option.R==1){
printdirectory(list, option);
}
free(l[j]);
}
free(l);
return(0);
}
int main(int argc, char *argv[]){
struct stat s;
int i;
struct options option={0,0,0,0,0,0,0};
char opt;
opterr=0;
while ((opt=getopt(argc, argv, "Rlnisda" )) != -1){
switch (opt){
case 'l': option.l=1; break;
case 'n': option.n=1; break;
case 'R': option.R=1; break;
case 'i': option.i=1; break;
case 's': option.s=1; break;
case 'd': option.d=1; break;
case 'a': option.a=1; break;
/* Afficher que l'option taper n'est pas utilisée */
default: fprintf(stderr,"option -%c non utilisee\n",opt);
}
}
if ((argc-optind)==0)
{
if (option.d) printfile(".",option);
else printdirectory(".", option);
}
for (i=optind; i<argc; i++){
if (lstat(argv[i], &s)){
fprintf(stderr,"%s: ", argv[i]);
perror("lstat()" );
continue;
}
if (!S_ISDIR(s.st_mode) || option.d){
printfile(argv[i],option);
printf("\n" );
}
else{
printdirectory(argv[i], option);
}
}
return(0);
}