PDA

Visualizza la versione completa : [C] Lseek non funziona bene


LeDaVinci
27-03-2006, 21:39
#include <sys/types.h>
#include <sys/stat.h>
#include <asm/fcntl.h>
#include <unistd.h>
#include <stdio.h>

int main()
{
int fd,n,d;
char s[20];
char *p;
off_t i;

if((fd=open("file.c",O_RDWR|O_CREAT,0664))<0)
printf("errore nella open \n");

printf("Scrivi nel file \n");
n=read(STDIN_FILENO,s,20);
write(fd,s,n);
i=lseek(fd,10,SEEK_CUR);
printf("Scrivi dopo il buco \n");
d=read(STDIN_FILENO,p,20);
write(fd,p,d);
return (0);
}

è semplicissimo ma dopo averlo eseguito se apro "file.c" mi dice: il file://home...../file.c è binario, salvandolo otterai un file danneggiato. Il file contiene quello che ho scritto sulla linea di comando ma se voglio modificarlo direttamente non me lo fa fare in realtà su questo file dopo non mi fa fare niente. PERCHE'??

LeDaVinci
28-03-2006, 09:27
allora ragazzi nessuno può aiutarmi!!

Samuele_70
28-03-2006, 11:34
Sinceramente non si capisce cosa dovrebbe fare il codice che hai postato.
Innanzi tutto che compilatore usi ? (visto gli 'strani' include che usi)
Cosè "STDIN_FILENO" ? A quale stream corrisponde, è tipo stdin ?
Devi chiarire meglio qual'è il problema, o nessuno potrà aiutarti :bhò:

LeDaVinci
28-03-2006, 17:14
Originariamente inviato da Samuele_70
Sinceramente non si capisce cosa dovrebbe fare il codice che hai postato.
Innanzi tutto che compilatore usi ? (visto gli 'strani' include che usi)
Cosè "STDIN_FILENO" ? A quale stream corrisponde, è tipo stdin ?
Devi chiarire meglio qual'è il problema, o nessuno potrà aiutarti :bhò:

il codice non fa nulla di particolare: creo un file ci scrivo dentro quello che ho letto da input(STDIN_FILENO) mi sposto con la lseek e poi riscrivo quello che rileggo da tastiera!! utilizzo per compilare gcc!

Samuele_70
28-03-2006, 18:54
Originariamente inviato da LeDaVinci
il codice non fa nulla di particolare: creo un file ci scrivo dentro quello che ho letto da input(STDIN_FILENO) mi sposto con la lseek e poi riscrivo quello che rileggo da tastiera!! utilizzo per compilare gcc!
Infatti anche con g++ (MinGW) compila.
Così funziona, la prima stringa però deve essere >=10, altrimenti andresti a scrivere oltre la fine del file, con
la successiva write().


#include <sys/types.h>
#include <sys/stat.h>
#include <stdio.h>
#include <fcntl.h>
#include <io.h>

int main()
{
int fd, n, d;
const int slen = 80;
char s[slen];
off_t i;
fd = open("file.c", O_TEXT | O_RDWR | O_CREAT, S_IREAD | S_IWRITE);
if( fd >= 0 )
{
printf("Scrivi nel file \n\n");
n = read( STDIN_FILENO, s, slen);
// write( fd, s, n-1); // Con n-1 non scrivo il carattere invio
write( fd, s, n-1); // Con n-1 non scrivo il carattere invio
// i = lseek( fd, 10, SEEK_CUR); // +10 dalla posizione attuale !
i = lseek( fd, 10, SEEK_SET); // +10 dalla posizione iniziale
printf("\nScrivi dopo il buco \n\n");
printf("Posizione nel file = %d\n", i);
n = read( STDIN_FILENO, s, slen);
write(fd, s, n-1); // Con n-1 non scrivo il carattere invio
close ( fd );
}
else
printf("\nErrore nella open() \n");
return 0;
}

Come vedi o usato "i = lseek( fd, 10, SEEK_SET)"
perchè con "i = lseek( fd, 10, SEEK_CUR)" ti spostavi
10 bytes oltre la posizione corrente, quindi anche oltre la
fine del file, ovvio che poi non scriveva nulla.

LeDaVinci
29-03-2006, 12:05
ok !! GRAZIE

LeDaVinci
29-03-2006, 17:58
scusa ma con la lseek non posso andare anche oltre e poi scrivere?? mi pare che così mi ha speiegato!! :dhò:

Samuele_70
29-03-2006, 19:50
Originariamente inviato da LeDaVinci
scusa ma con la lseek non posso andare anche oltre e poi scrivere?? mi pare che così mi ha speiegato!! :dhò:
Sei sicuro? Da quel che ne so io, non è possibile (puoi verificare da te)

Se ti posizioni esattamente alla fine del file


i = lseek( fd, 0, SEEK_END);

La seconda stringa viene aggiunta correttamente.

Ma se avanzi anche di un solo byte


i = lseek( fd, 1, SEEK_END);

La scrittura fallisce.

Se vuoi scrivere oltre devi appendere in coda al file dei
caratteri di spazio o di invio o tabulazione, così da non
lasciare un 'buco', e poi in coda potrai appendere la seconda stringa.

Ma perchè invece di open() e lseek() non standard ANSI,
non utilizzi le equivalenti fopen() e fseek() ?

LeDaVinci
30-03-2006, 11:14
Originariamente inviato da Samuele_70
Sei sicuro? Da quel che ne so io, non è possibile (puoi verificare da te)

Se ti posizioni esattamente alla fine del file


i = lseek( fd, 0, SEEK_END);

La seconda stringa viene aggiunta correttamente.

Ma se avanzi anche di un solo byte


i = lseek( fd, 1, SEEK_END);

La scrittura fallisce.

Se vuoi scrivere oltre devi appendere in coda al file dei
caratteri di spazio o di invio o tabulazione, così da non
lasciare un 'buco', e poi in coda potrai appendere la seconda stringa.

Ma perchè invece di open() e lseek() non standard ANSI,
non utilizzi le equivalenti fopen() e fseek() ?

perchè devo afre l'esame di Laboratorio di Sistemi Operativi e devo fare programmi che usano le system call!!cmq quando eseguo il tuo programma funziona ma quando vado ad aprire il file mi dice che il file è binario e se lo salvo mi crea un file danneggiato e non mi fa compiere nessuna operazione sul file aperto!! come mai?? però questo problema me lo dà solo se utilizzo la lseek perchè se creo e scrivo su un file non mi dice niente ed il file creato è perfettamente integro!!

murder eyes
30-03-2006, 21:58
Se utilizzi un file binario non sono sicuro che tu possa utilizzare la funzione lseek.
Cmq non è assolutamente fare uso sia di funzioni bufferizzate e formattate, insieme a chiamate di sistema: puoi incorrere in casi molto particolari, perchè ad esempio non è dedicibile il momento in cui ad esempio una write(che è una SC) svuota il buffer di scrittura.

Loading