Advertisement
Guest User

Untitled

a guest
Dec 11th, 2019
95
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 8.48 KB | None | 0 0
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include "locale.h"
  4. #include "malloc.h"
  5. #include <string.h>
  6. #include <math.h>
  7.  
  8. /*
  9. file structure:
  10. ID3v2/file identifier "ID3"
  11. ID3v2 version $03 00
  12. ID3v2 flags %abc00000
  13. ID3v2 size 4 * %0xxxxxxx
  14.  
  15. Frame ID $xx xx xx xx (four characters)
  16. Size $xx xx xx xx
  17. Flags $xx xx
  18.  
  19. <Frame contents>
  20.  
  21. etc...
  22. */
  23.  
  24. int buffToIntegerForFrame(unsigned char *bytes) //char to integer size
  25. {
  26. return
  27. bytes[0] * pow(2, 24) + //2^21
  28. bytes[1] * pow(2, 16) + //2^14
  29. bytes[2] * pow(2, 8) + //2^7
  30. bytes[3];
  31. }
  32.  
  33. int buffToInteger(unsigned char *bytes) {
  34. return
  35. bytes[0] * 0x200000 + //2^21
  36. bytes[1] * 0x4000 + //2^14
  37. bytes[2] * 0x80 + //2^7
  38. bytes[3];
  39. }
  40.  
  41. void integerToBuff(int number, unsigned char *result) {
  42. result[0] = (unsigned char) ((number & 0xfe00000) >> 21); //0100000
  43. result[1] = (unsigned char) ((number & 0x1fc000) >> 14); //0010010
  44. result[2] = (unsigned char) ((number & 0x3f80) >> 7); //0000001
  45. result[3] = (unsigned char) (number & 0x7f); //0000100
  46. }
  47.  
  48. void integerToBuffForFrame(int number, unsigned char *result) {
  49. result[0] = (unsigned char) ((number & 0xff000000) >> 24); //0100000
  50. result[1] = (unsigned char) ((number & 0xff0000) >> 16); //0010010
  51. result[2] = (unsigned char) ((number & 0xff00) >> 8); //0000001
  52. result[3] = (unsigned char) (number & 0xff); //0000100
  53. }
  54.  
  55. struct tagHeader {
  56. unsigned char name[3]; //ID3
  57. unsigned char version[2]; //2 bytes ex. 3 0
  58. unsigned char flags; //1 byte
  59. unsigned int framesCount;
  60. unsigned int size; //4 bytes for tagHeader`s size
  61. };
  62. struct oframe {
  63. unsigned char name[4];//4 bytes FRAME NAME ex. TIT2, TALB and etc.
  64. unsigned char flags[2]; //2 bytes
  65. unsigned int size; //4 FRAME`S size
  66. unsigned char enc; //1 encoding
  67. unsigned char *content; //container
  68. };
  69.  
  70. void readBytes(unsigned char *res, unsigned int size, FILE *file) {
  71. for (int i = 0; i < size; i++) {
  72. res[i] = getc(file);
  73. }
  74. }
  75.  
  76. void writeBytes(unsigned char *res, unsigned int size, FILE *file) {
  77. for (int i = 0; i < size; i++) {
  78. putc(res[i], file);
  79. }
  80. }
  81.  
  82. struct tagHeader readTagHeader(FILE *file) //function
  83. {
  84. struct tagHeader tag;
  85. unsigned char flags[1]; // flags
  86. unsigned char sizeb[4]; // tag size in bytes
  87. readBytes(tag.name, 3, file);
  88. readBytes(tag.version, 2, file);
  89. readBytes(flags, 1, file);
  90. readBytes(sizeb, 4, file);
  91. tag.flags = flags[0];
  92. tag.size = buffToInteger(sizeb);
  93. return tag;
  94. }
  95.  
  96. void writeTagHeader(FILE *file, struct tagHeader tag) //function
  97. {
  98. unsigned char flags[1]; // flags
  99. unsigned char sizeb[4]; // tag size in bytes
  100. writeBytes(tag.name, 3, file);
  101. writeBytes(tag.version, 2, file);
  102. flags[0] = tag.flags;
  103. writeBytes(flags, 1, file);
  104. integerToBuff(tag.size, sizeb);
  105. writeBytes(sizeb, 4, file);
  106. }
  107.  
  108. void writeFrame(FILE *file, struct oframe frame) //function
  109. {
  110. unsigned char sizeb[4]; // tag size in bytes
  111. unsigned char enc[1]; // tag size in bytes
  112. writeBytes(frame.name, 4, file);
  113. integerToBuffForFrame(frame.size, sizeb);
  114. writeBytes(sizeb, 4, file);
  115. writeBytes(frame.flags, 2, file);
  116. enc[0] = frame.enc;
  117. writeBytes(enc, 1, file);
  118. writeBytes(frame.content, frame.size - 1, file);
  119. }
  120.  
  121. int checkName(char *name) {
  122. for (int i = 0; i < strlen(name); i++) {
  123. if ((name[i] < 60 | name[i] > 90) & (name[i] > 57 | name[i] < 48)) {
  124. return 0;
  125. }
  126. }
  127. return 1;
  128. }
  129.  
  130. struct oframe readoframe(FILE *file, int readedBytes) {
  131. struct oframe frame;
  132. unsigned char sizeb[4]; // tag size in bytes
  133. readBytes(frame.name, 4, file);
  134. readBytes(sizeb, 4, file);
  135. frame.size = buffToIntegerForFrame(sizeb);
  136. if (frame.size + 10 > readedBytes | frame.size == 0 | frame.size > 134 * pow(10, 5) | checkName(frame.name) == 0) {
  137. fseek(file, frame.size + 2, SEEK_CUR);
  138. frame.size = 0;
  139. return frame;
  140. }
  141. frame.content = malloc(frame.size);
  142. readBytes(frame.flags, 2, file);
  143. unsigned char enc[1];
  144. readBytes(enc, 1, file);
  145. frame.enc = enc[0];
  146. readBytes(frame.content, frame.size - 1, file);
  147. return frame;
  148. }
  149.  
  150. void set(char *filepath, char *framename, char *value) {
  151. FILE *fp = fopen(filepath, "rb");
  152. struct tagHeader tag = readTagHeader(fp);
  153. int old_size = tag.size;
  154. tag.framesCount = 0;
  155. //END OF TAG HEADER
  156. int diff = 0;
  157. int bytesReaded = 10;
  158. struct oframe frames[tag.size / 11 + 1];
  159. int i = 0;
  160. while (tag.size > bytesReaded) {
  161. frames[tag.framesCount] = readoframe(fp, tag.size - bytesReaded);
  162. if (frames[tag.framesCount].size == 0) {
  163. break;
  164. }
  165. bytesReaded += 10 + frames[tag.framesCount].size;
  166. tag.framesCount += 1;
  167. }
  168. //END OF READING METADATA FROM FILE
  169. //BEGIN OF WRITING NEW FILE
  170. remove("temp.mp3");
  171. FILE *outf = fopen("temp.mp3", "wb");
  172. writeTagHeader(outf, tag);
  173. for (int i = 0; i < tag.framesCount; i++) {
  174. if (strcmp(frames[i].name, framename) == 0) {
  175. diff = strlen(value) - strlen(frames[i].content);
  176. tag.size += diff;
  177. strcpy(frames[i].content, value);
  178. frames[i].size = strlen(value) + 1;
  179. }
  180. writeFrame(outf, frames[i]);
  181. /*printf("%s %d ", frames[i].name, frames[i].size);
  182. for (int j = 0; j < frames[i].size; j++) {
  183. printf("%c", frames[i].content[j]);
  184. }
  185. printf("\n");*/
  186. }
  187. int pos;
  188. pos = ftell(outf);
  189. int countzeros = 10 + tag.size - ((int) pos);
  190. unsigned char zeros[countzeros];
  191. for (int i = 0; i < countzeros; i++) {
  192. zeros[i] = 0;
  193. }
  194. writeBytes(zeros, countzeros, outf);
  195. char tmp;
  196. fseek(fp, old_size + 10, SEEK_SET);
  197. fseek(outf, tag.size + 10, SEEK_SET);
  198. tmp = fgetc(fp);
  199. while (!feof(fp)){
  200. fputc(tmp, outf);
  201. tmp = fgetc(fp);
  202. }
  203. fclose(outf);
  204. fclose(fp);
  205. }
  206.  
  207. void get(char *filepath, char *framename) {
  208. FILE *fp = fopen(filepath, "rb");
  209. struct tagHeader tag = readTagHeader(fp);
  210. //END OF TAG HEADER
  211.  
  212. int bytesReaded = 10;
  213. struct oframe frames[tag.size / 11 + 1];
  214. int i = 0;
  215.  
  216. while (tag.size > bytesReaded) {
  217. struct oframe buff = readoframe(fp, tag.size - bytesReaded);
  218. if (buff.size == 0)
  219. break;
  220.  
  221. frames[i] = buff;
  222. if (strcmp(frames[i].name, framename) == 0) {
  223. printf("%s data: ", framename);
  224. for (int j = 0; j < frames[i].size - 1; j++) {
  225. printf("%c", frames[i].content[j]);
  226. }
  227.  
  228. i++;
  229. for (int j = 0; j < buff.size; ++j) //clearing buff container
  230. buff.content[j] = 0;
  231. printf("\n");
  232. break;
  233. }
  234. }
  235. }
  236.  
  237. void show(char *filepath) {
  238. FILE *fp = fopen(filepath, "rb");
  239. struct tagHeader tag = readTagHeader(fp);
  240. printf("%s%s%d%d%s%d\n", tag.name, " : ", tag.version[0], tag.version[1], " : ", tag.size);
  241. //END OF TAG HEADER
  242.  
  243. int bytesReaded = 10;
  244. struct oframe frames[tag.size / 11 + 1];
  245. int i = 0;
  246.  
  247. while (tag.size > bytesReaded) {
  248. struct oframe buff = readoframe(fp, tag.size - bytesReaded);
  249. if (buff.size == 0)
  250. break;
  251.  
  252. frames[i] = buff;
  253. printf("%s %d ", frames[i].name, frames[i].size);
  254. bytesReaded += 10 + frames[i].size;
  255. for (int j = 0; j < frames[i].size - 1; j++)
  256. printf("%c", frames[i].content[j]);
  257.  
  258. i++;
  259. for (int j = 0; j < buff.size; ++j) //clearing buff container
  260. buff.content[j] = 0;
  261. printf("\n");
  262.  
  263.  
  264. }
  265. //END OF FRAME
  266.  
  267. }
  268.  
  269. int main(int argc, char *argv[]) {
  270. setlocale(LC_ALL, "Rus");
  271. char* filepath;
  272. filepath = strpbrk(argv[1],"=") + 1;
  273. for (int i = 2; i < argc; i++){
  274. if (strcmp(argv[i], "--show") == 0) {
  275. show(filepath);
  276. continue;
  277. }
  278. if (strcmp(argv[i], "--get") == 0) {
  279. get(filepath, argv[i+1]);
  280. continue;
  281. }
  282. if (strcmp(argv[i], "--set") == 0) {
  283. set(filepath, argv[i+1], argv[i+2]);
  284. continue;
  285. }
  286. }
  287. return 0;
  288. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement