Skip to content

Commit

Permalink
0.20230107: standard fopen
Browse files Browse the repository at this point in the history
  • Loading branch information
zvezdochiot committed Jan 7, 2023
1 parent 7d4d06e commit ee04fdf
Show file tree
Hide file tree
Showing 5 changed files with 159 additions and 112 deletions.
5 changes: 2 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,9 @@ $ sudo ln -s /usr/share/man/man1/torreadwrite.1.gz /usr/share/man/man1/torwrite.
### SAMPLE

```shell
$ torread samplefile.torrent > samplefile.torrent.txt
$ torread samplefile.torrent samplefile.torrent.txt
$ nano samplefile.torrent.txt

$ torwrite samplefile.torrent.txt > samplefile.mod.torrent
$ torwrite samplefile.torrent.txt samplefile.mod.torrent
```

### STRUCTURE
Expand Down
10 changes: 5 additions & 5 deletions man/man1/torreadwrite.1
Original file line number Diff line number Diff line change
Expand Up @@ -9,29 +9,29 @@ Utilities \fItorread\fR for decoding and \fItorwrite\fR for encoding \fI.torrent
.SH SYNOPSIS
.PP
.B torread
file.torrent > file.txt
file.torrent file.txt
.PP
.B torwrite
file.txt > file.torrent
file.txt file.torrent

.SH OPTIONS
None.

.SH EXAMPLE
.B torread
samplefile.torrent > samplefile.torrent.txt
samplefile.torrent samplefile.torrent.txt
.PP
.B nano
samplefile.torrent.txt
.PP
.B torwrite
samplefile.torrent.txt > samplefile.mod.torrent
samplefile.torrent.txt samplefile.mod.torrent

.SH COPYRIGHT
This is free and unencumbered software released into the public domain.

.SH SEE ALSO
ctorrent(1), aria2c(1), torrentcheck(7), torreadwrite(7)
ctorrent(1), aria2c(1), torrentcheck(1), torreadwrite(7)

.SH CONTACTS
Website: https://github.com/Network-BEncode-inside/torreadwrite
9 changes: 4 additions & 5 deletions man/man7/torreadwrite.7
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
.TH torreadwrite 7 "0.20230107" "07 Jan 2023" "Development Manual"

.SH NAME

torreadwrite

.SH ABOUT
.PP
VL-LUG
.PP
Expand All @@ -14,22 +15,20 @@ SRC: http://linuxdv.ru/forum/download/file.php?id=28
.PP

.SH SAMPLE

$
.B torread
samplefile.torrent > samplefile.torrent.txt
samplefile.torrent samplefile.torrent.txt
.PP
$
.B nano
samplefile.torrent.txt
.PP
$
.B torwrite
samplefile.torrent.txt > samplefile.mod.torrent
samplefile.torrent.txt samplefile.mod.torrent
.PP

.SH STRUCTURE

Content torrent file
.PP
Content torrent file is encoded as described above. Himself torrent file is bencoded dictionary with the following keys:
Expand Down
161 changes: 93 additions & 68 deletions src/torread.c
Original file line number Diff line number Diff line change
@@ -1,11 +1,9 @@
/* $Id: torread.c 529 2009-09-11 08:44:53Z michael $ */
#include <fcntl.h>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <unistd.h>

const uint8_t sp=' ';
const uint8_t ret='\n';
Expand All @@ -20,27 +18,27 @@ const uint8_t eqv='=';

enum obj_type {OBJ_NUL, OBJ_INT, OBJ_STR, OBJ_LST, OBJ_DCT};

void Byte2Hex(uint8_t ch);
void PrintSpc(int num);
void Byte2Hex(uint8_t ch,FILE* fdo);
void PrintSpc(int num,FILE* fdo);
enum obj_type DetType(const uint8_t* d, size_t shift);
size_t FindSym(const uint8_t* d, uint8_t s, size_t shift, size_t len);
size_t PrintInt(const uint8_t* d, size_t shift, size_t len);
size_t PrintStr(const uint8_t* d, size_t shift, size_t len);
size_t PrintLst(const uint8_t* d, size_t shift, size_t len, int skip);
size_t PrintDct(const uint8_t* d, size_t shift, size_t len, int skip);
size_t PrintObj(const uint8_t* d, size_t shift, size_t len, int skip);
size_t PrintInt(const uint8_t* d, size_t shift, size_t len,FILE* fdo);
size_t PrintStr(const uint8_t* d, size_t shift, size_t len,FILE* fdo);
size_t PrintLst(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo);
size_t PrintDct(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo);
size_t PrintObj(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo);

void Byte2Hex(uint8_t ch)
void Byte2Hex(uint8_t ch,FILE* fdo)
{
static const uint8_t cnv[]= {'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
fwrite(cnv + (( ch & (15 << 4)) >> 4), 1, 1, stdout);
fwrite(cnv + (ch & 15), 1, 1, stdout);
fwrite(cnv + (( ch & (15 << 4)) >> 4), 1, 1, fdo);
fwrite(cnv + (ch & 15), 1, 1, fdo);
}

void PrintSpc(int num)
void PrintSpc(int num,FILE* fdo)
{
int i;
for(i = 0; i < num; i++) fwrite(&sp, 1, 1, stdout);
for(i = 0; i < num; i++) fwrite(&sp, 1, 1, fdo);
}

enum obj_type DetType(const uint8_t* d, size_t shift)
Expand All @@ -61,140 +59,167 @@ size_t FindSym(const uint8_t* d, uint8_t s, size_t shift, size_t len)
exit(2);
}

size_t PrintObj(const uint8_t* d, size_t shift, size_t len, int skip)
size_t PrintObj(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo)
{
switch(DetType(d, shift))
{
case(OBJ_NUL):
exit(2);
case(OBJ_INT):
return PrintInt(d, shift, len);
return PrintInt(d, shift, len, fdo);
case(OBJ_STR):
return PrintStr(d, shift, len);
return PrintStr(d, shift, len, fdo);
case(OBJ_LST):
return PrintLst(d, shift, len, skip);
return PrintLst(d, shift, len, skip, fdo);
case(OBJ_DCT):
return PrintDct(d, shift, len, skip);
return PrintDct(d, shift, len, skip, fdo);
}
exit(2);
}

size_t PrintInt(const uint8_t* d, size_t shift, size_t len)
size_t PrintInt(const uint8_t* d, size_t shift, size_t len,FILE* fdo)
{
size_t e = FindSym(d, 'e', shift, len);
fwrite(d + shift + 1, e - shift - 1, 1, stdout);
fwrite(d + shift + 1, e - shift - 1, 1, fdo);
return e+1;
}

size_t PrintStr(const uint8_t* d, size_t shift, size_t len)
size_t PrintStr(const uint8_t* d, size_t shift, size_t len,FILE* fdo)
{
size_t e = FindSym(d, ':', shift, len);
int l = atoi((const char*)(d + shift));
if(e + l >= len) exit(2);
size_t p;

fwrite(&quo, 1, 1, stdout);
fwrite(&quo, 1, 1, fdo);
for(p = e + 1; p <= e + l; p++)
{
if(d[p] == 127 || d[p] < 32)
{
fwrite(&scr, 1, 1, stdout);
fwrite(&hxp, 1, 1, stdout);
Byte2Hex(d[p]);
fwrite(&scr, 1, 1, fdo);
fwrite(&hxp, 1, 1, fdo);
Byte2Hex(d[p], fdo);
}
else if(d[p] == '\\')
{
fwrite(&scr, 1, 1, stdout);
fwrite(&scr, 1, 1, stdout);
fwrite(&scr, 1, 1, fdo);
fwrite(&scr, 1, 1, fdo);
}
else if(d[p] == '\"')
{
fwrite(&scr, 1, 1, stdout);
fwrite(&quo, 1, 1, stdout);
fwrite(&scr, 1, 1, fdo);
fwrite(&quo, 1, 1, fdo);
}
else fwrite(d + p, 1, 1, stdout);
else fwrite(d + p, 1, 1, fdo);
}

fwrite(&quo, 1, 1, stdout);
fwrite(&quo, 1, 1, fdo);
return e + l + 1;
}

size_t PrintLst(const uint8_t* d, size_t shift, size_t len, int skip)
size_t PrintLst(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo)
{
size_t ishift=shift+1;

fwrite(&blst, 1, 1, stdout);
fwrite(&ret, 1, 1, stdout);
fwrite(&blst, 1, 1, fdo);
fwrite(&ret, 1, 1, fdo);

while(d[ishift] != 'e')
{
PrintSpc(skip + 1);
ishift = PrintObj(d, ishift, len, skip + 1);
fwrite(&ret, 1, 1, stdout);
PrintSpc(skip + 1, fdo);
ishift = PrintObj(d, ishift, len, skip + 1, fdo);
fwrite(&ret, 1, 1, fdo);
if(ishift >= len) exit(2);
}
PrintSpc(skip);
fwrite(&elst, 1, 1, stdout);
PrintSpc(skip, fdo);
fwrite(&elst, 1, 1, fdo);
return ishift + 1;
}

size_t PrintDct(const uint8_t* d, size_t shift, size_t len, int skip)
size_t PrintDct(const uint8_t* d, size_t shift, size_t len, int skip,FILE* fdo)
{
size_t ishift = shift + 1;

fwrite(&bdct, 1, 1, stdout);
fwrite(&ret, 1, 1, stdout);
fwrite(&bdct, 1, 1, fdo);
fwrite(&ret, 1, 1, fdo);

while(d[ishift] != 'e')
{
PrintSpc(skip + 1);
PrintSpc(skip + 1, fdo);
if(DetType(d, ishift) != OBJ_STR) exit(2);
ishift = PrintStr(d, ishift, len);
fwrite(&sp, 1, 1, stdout);
fwrite(&eqv, 1, 1, stdout);
fwrite(&sp, 1, 1, stdout);
ishift = PrintObj(d, ishift, len, skip + 1);
fwrite(&ret, 1, 1, stdout);
ishift = PrintStr(d, ishift, len, fdo);
fwrite(&sp, 1, 1, fdo);
fwrite(&eqv, 1, 1, fdo);
fwrite(&sp, 1, 1, fdo);
ishift = PrintObj(d, ishift, len, skip + 1, fdo);
fwrite(&ret, 1, 1, fdo);
if(ishift >= len) exit(2);
}
PrintSpc(skip);
fwrite(&edct, 1, 1, stdout);
PrintSpc(skip, fdo);
fwrite(&edct, 1, 1, fdo);
return ishift + 1;
}

int main(int argc, char** argv)
{
if(argc != 2)
if(argc < 3)
{
fprintf(stderr, "Usage: %s file.torrent > file.torrent.txt", argv[0]);
fprintf(stderr, "Usage: %s file.torrent file.txt\n", argv[0]);
return 1;
}

int fd;
struct stat st;
FILE *fd, *fdo;
uint8_t *pdata;
size_t flen = 0;

fd = open(argv[1],O_RDONLY);
if(fd == -1)
fd = fopen(argv[1],"rb");
if(fd == NULL)
{
fprintf(stderr, "ERROR: Can't open %s", argv[1]);
return 1;
}
if(fstat(fd, &st) != 0)
fdo = fopen(argv[2],"wb");
if(fdo == NULL)
{
fprintf(stderr, "ERROR: Can't read %s", argv[1]);
fprintf(stderr, "ERROR: Can't write %s", argv[2]);
return 1;
}
if(st.st_size == 0)

fseek(fd,0l,SEEK_END);
flen = ftell(fd);
if(flen == 0)
{
fprintf(stderr, "ERROR: File %s empty", argv[1]);
return 1;
}
pdata = (uint8_t*) mmap(0, st.st_size, PROT_READ, MAP_SHARED, fd, 0);
PrintDct(pdata, 0, st.st_size, 0);
fwrite(&ret, 1, 1, stdout);
munmap(pdata, st.st_size);
close(fd);
if (flen > 16777216)
{
printf("Torrent metadata file %s is %ld bytes long.\n",argv[1],flen);
printf("That is unusually large for a torrent file. You may have specified an\n");
printf("incorrect file. The metadata must be loaded into memory, so this may\n");
printf("take some time or fail due to lack of memory.\n");
printf("\n");
}
rewind(fd);

pdata = malloc(flen);
if (pdata == NULL)
{
printf("Unable to malloc %ld bytes for torrent file\n",flen);
return 2;
}
flen = fread(pdata,1,flen,fd);
if(flen == 0)
{
fprintf(stderr, "ERROR: File %s empty", argv[1]);
return 1;
}

PrintDct(pdata, 0, flen, 0, fdo);
fwrite(&ret, 1, 1, fdo);
free(pdata);
fclose(fd);
fclose(fdo);

return 0;
}
Loading

0 comments on commit ee04fdf

Please sign in to comment.