You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

277 lines
7.1KB

  1. #include <stdint.h>
  2. #include "sockutil.h"
  3. #include "sys/pollfd.h"
  4. #include "sys/thread.h"
  5. #include "rtp-demuxer.h"
  6. #include "rtp-profile.h"
  7. #include "rtp-payload.h"
  8. #include "rtcp-header.h"
  9. #include "rtp.h"
  10. #include "time64.h"
  11. #include <stdio.h>
  12. #include <stdlib.h>
  13. #include <string.h>
  14. #include <assert.h>
  15. #if defined(OS_WINDOWS)
  16. #define strcasecmp _stricmp
  17. #endif
  18. struct rtp_context_t
  19. {
  20. FILE *fp;
  21. FILE *frtp;
  22. char encoding[64];
  23. socket_t socket[2];
  24. struct sockaddr_storage ss[2];
  25. char rtp_buffer[64 * 1024];
  26. char rtcp_buffer[32 * 1024];
  27. struct rtp_demuxer_t* demuxer;
  28. };
  29. static int rtp_read(struct rtp_context_t* ctx, socket_t s)
  30. {
  31. int r;
  32. uint8_t size[2];
  33. static int i, n = 0;
  34. socklen_t len;
  35. struct sockaddr_storage ss;
  36. len = sizeof(ss);
  37. r = recvfrom(s, ctx->rtp_buffer, sizeof(ctx->rtp_buffer), 0, (struct sockaddr*)&ss, &len);
  38. if (r < 12)
  39. return -1;
  40. assert(0 == socket_addr_compare((const struct sockaddr*) & ss, (const struct sockaddr*) & ctx->ss[0]));
  41. n += r;
  42. if(0 == i++ % 100)
  43. printf("packet: %d, seq: %u, size: %d/%d\n", i, ((uint8_t)ctx->rtp_buffer[2] << 8) | (uint8_t)ctx->rtp_buffer[3], r, n);
  44. size[0] = r >> 8;
  45. size[1] = r >> 0;
  46. fwrite(size, 1, sizeof(size), ctx->frtp);
  47. fwrite(ctx->rtp_buffer, 1, r, ctx->frtp);
  48. r = rtp_demuxer_input(ctx->demuxer, ctx->rtp_buffer, r);
  49. return r;
  50. }
  51. static int rtcp_read(struct rtp_context_t* ctx, socket_t s)
  52. {
  53. int r;
  54. socklen_t len;
  55. struct sockaddr_storage ss;
  56. len = sizeof(ss);
  57. r = recvfrom(s, ctx->rtcp_buffer, sizeof(ctx->rtcp_buffer), 0, (struct sockaddr*)&ss, &len);
  58. if (r < 12)
  59. return -1;
  60. assert(0 == socket_addr_compare((const struct sockaddr*)&ss, (const struct sockaddr*)&ctx->ss[1]));
  61. r = rtp_demuxer_input(ctx->demuxer, ctx->rtcp_buffer, r);
  62. if (RTCP_BYE == r)
  63. {
  64. printf("finished\n");
  65. }
  66. fflush(ctx->fp);
  67. return r;
  68. }
  69. static int rtp_receiver(struct rtp_context_t* ctx, socket_t rtp[2], int timeout)
  70. {
  71. int i, r;
  72. // int interval;
  73. time64_t clock;
  74. struct pollfd fds[2];
  75. for (i = 0; i < 2; i++)
  76. {
  77. fds[i].fd = rtp[i];
  78. fds[i].events = POLLIN;
  79. fds[i].revents = 0;
  80. }
  81. clock = time64_now();
  82. while (1)
  83. {
  84. // RTCP report
  85. r = rtp_demuxer_rtcp(ctx->demuxer, ctx->rtcp_buffer, sizeof(ctx->rtcp_buffer));
  86. if (r > 0)
  87. r = socket_sendto(rtp[1], ctx->rtcp_buffer, r, 0, (const struct sockaddr*) & ctx->ss[1], socket_addr_len((const struct sockaddr*) & ctx->ss[1]));
  88. r = poll(fds, 2, timeout);
  89. while (-1 == r && EINTR == errno)
  90. r = poll(fds, 2, timeout);
  91. if (0 == r)
  92. {
  93. continue; // timeout
  94. }
  95. else if (r < 0)
  96. {
  97. return r; // error
  98. }
  99. else
  100. {
  101. if (0 != fds[0].revents)
  102. {
  103. rtp_read(ctx, rtp[0]);
  104. fds[0].revents = 0;
  105. }
  106. if (0 != fds[1].revents)
  107. {
  108. rtcp_read(ctx, rtp[1]);
  109. fds[1].revents = 0;
  110. }
  111. }
  112. }
  113. return r;
  114. }
  115. static int rtp_onpacket(void* param, const void *packet, int bytes, uint32_t timestamp, int flags)
  116. {
  117. const uint8_t start_code[] = { 0, 0, 0, 1 };
  118. struct rtp_context_t* ctx;
  119. ctx = (struct rtp_context_t*)param;
  120. if (0 == strcmp("H264", ctx->encoding) || 0 == strcmp("H265", ctx->encoding))
  121. {
  122. fwrite(start_code, 1, 4, ctx->fp);
  123. }
  124. else if (0 == strcasecmp("mpeg4-generic", ctx->encoding))
  125. {
  126. uint8_t adts[7];
  127. int len = bytes + 7;
  128. uint8_t profile = 2;
  129. uint8_t sampling_frequency_index = 4;
  130. uint8_t channel_configuration = 2;
  131. adts[0] = 0xFF; /* 12-syncword */
  132. adts[1] = 0xF0 /* 12-syncword */ | (0 << 3)/*1-ID*/ | (0x00 << 2) /*2-layer*/ | 0x01 /*1-protection_absent*/;
  133. adts[2] = ((profile - 1) << 6) | ((sampling_frequency_index & 0x0F) << 2) | ((channel_configuration >> 2) & 0x01);
  134. adts[3] = ((channel_configuration & 0x03) << 6) | ((len >> 11) & 0x03); /*0-original_copy*/ /*0-home*/ /*0-copyright_identification_bit*/ /*0-copyright_identification_start*/
  135. adts[4] = (uint8_t)(len >> 3);
  136. adts[5] = ((len & 0x07) << 5) | 0x1F;
  137. adts[6] = 0xFC | ((len / 1024) & 0x03);
  138. fwrite(adts, 1, sizeof(adts), ctx->fp);
  139. }
  140. else if (0 == strcmp("MP4A-LATM", ctx->encoding))
  141. {
  142. // add ADTS header
  143. }
  144. fwrite(packet, 1, bytes, ctx->fp);
  145. (void)timestamp;
  146. (void)flags;
  147. if (0 == strcmp("H264", ctx->encoding))
  148. {
  149. uint8_t type = *(uint8_t*)packet & 0x1f;
  150. if (0 < type && type <= 5)
  151. {
  152. // VCL frame
  153. }
  154. }
  155. else if (0 == strcmp("H265", ctx->encoding))
  156. {
  157. uint8_t type = (*(uint8_t*)packet >> 1) & 0x3f;
  158. if (type <= 32)
  159. {
  160. // VCL frame
  161. }
  162. }
  163. return 0;
  164. }
  165. static int STDCALL rtp_worker(void* param)
  166. {
  167. struct rtp_context_t* ctx;
  168. ctx = (struct rtp_context_t*)param;
  169. rtp_receiver(ctx, ctx->socket, 2000);
  170. rtp_demuxer_destroy(&ctx->demuxer);
  171. fclose(ctx->frtp);
  172. fclose(ctx->fp);
  173. free(ctx);
  174. return 0;
  175. }
  176. void rtp_receiver_test(socket_t rtp[2], const char* peer, int peerport[2], int payload, const char* encoding)
  177. {
  178. size_t n;
  179. pthread_t t;
  180. struct rtp_context_t* ctx;
  181. const struct rtp_profile_t* profile;
  182. ctx = malloc(sizeof(*ctx));
  183. if(!ctx) return;
  184. snprintf(ctx->rtp_buffer, sizeof(ctx->rtp_buffer), "%s.%d.%d.%s", peer, peerport[0], payload, encoding);
  185. snprintf(ctx->rtcp_buffer, sizeof(ctx->rtcp_buffer), "%s.%d.%d.%s.rtp", peer, peerport[0], payload, encoding);
  186. ctx->fp = fopen(ctx->rtp_buffer, "wb");
  187. ctx->frtp = fopen(ctx->rtcp_buffer, "wb");
  188. socket_getrecvbuf(rtp[0], &n);
  189. socket_setrecvbuf(rtp[0], 512*1024);
  190. socket_getrecvbuf(rtp[0], &n);
  191. profile = rtp_profile_find(payload);
  192. ctx->demuxer = rtp_demuxer_create(100, profile ? profile->frequency : 90000, payload, encoding, rtp_onpacket, ctx);
  193. if (NULL == ctx->demuxer)
  194. return; // ignore
  195. assert(0 == socket_addr_from(&ctx->ss[0], NULL, peer, (u_short)peerport[0]));
  196. assert(0 == socket_addr_from(&ctx->ss[1], NULL, peer, (u_short)peerport[1]));
  197. //assert(0 == connect(rtp[0], (struct sockaddr*)&ctx->ss[0], len));
  198. //assert(0 == connect(rtp[1], (struct sockaddr*)&ctx->ss[1], len));
  199. snprintf(ctx->encoding, sizeof(ctx->encoding), "%s", encoding);
  200. ctx->socket[0] = rtp[0];
  201. ctx->socket[1] = rtp[1];
  202. if (0 == thread_create(&t, rtp_worker, ctx))
  203. thread_detach(t);
  204. }
  205. static struct rtp_context_t* s_ctx[8];
  206. void* rtp_receiver_tcp_test(uint8_t interleave1, uint8_t interleave2, int payload, const char* encoding)
  207. {
  208. struct rtp_context_t* ctx;
  209. const struct rtp_profile_t* profile;
  210. ctx = malloc(sizeof(struct rtp_context_t));
  211. if(!ctx) return NULL;
  212. snprintf(ctx->rtp_buffer, sizeof(ctx->rtp_buffer), "tcp.%d.%s", payload, encoding);
  213. snprintf(ctx->rtcp_buffer, sizeof(ctx->rtcp_buffer), "tcp.%d.%s.rtp", payload, encoding);
  214. ctx->fp = fopen(ctx->rtp_buffer, "wb");
  215. ctx->frtp = fopen(ctx->rtcp_buffer, "wb");
  216. snprintf(ctx->encoding, sizeof(ctx->encoding), "%s", encoding);
  217. assert(interleave1 / 2 < sizeof(s_ctx) / sizeof(s_ctx[0]));
  218. s_ctx[interleave1 / 2] = ctx;
  219. profile = rtp_profile_find(payload);
  220. ctx->demuxer = rtp_demuxer_create(100, profile ? profile->frequency : 90000, payload, encoding, rtp_onpacket, ctx);
  221. return ctx;
  222. }
  223. void rtp_receiver_tcp_input(uint8_t channel, const void* data, uint16_t bytes)
  224. {
  225. int r;
  226. uint8_t size[2];
  227. struct rtp_context_t* ctx = s_ctx[channel / 2];
  228. if (0 == channel % 2)
  229. {
  230. size[0] = bytes >> 8;
  231. size[1] = bytes >> 0;
  232. fwrite(size, 1, sizeof(size), ctx->frtp);
  233. fwrite(data, 1, bytes, ctx->frtp);
  234. }
  235. if (ctx->demuxer)
  236. {
  237. r = rtp_demuxer_input(ctx->demuxer, data, bytes);
  238. assert(r >= 0);
  239. }
  240. }