520-uniq.patch 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269
  1. --- a/pppd/plugins/rp-pppoe/common.c
  2. +++ b/pppd/plugins/rp-pppoe/common.c
  3. @@ -119,15 +119,11 @@ sendPADT(PPPoEConnection *conn, char con
  4. conn->session = 0;
  5. /* If we're using Host-Uniq, copy it over */
  6. - if (conn->useHostUniq) {
  7. - PPPoETag hostUniq;
  8. - pid_t pid = getpid();
  9. - hostUniq.type = htons(TAG_HOST_UNIQ);
  10. - hostUniq.length = htons(sizeof(pid));
  11. - memcpy(hostUniq.payload, &pid, sizeof(pid));
  12. - memcpy(cursor, &hostUniq, sizeof(pid) + TAG_HDR_SIZE);
  13. - cursor += sizeof(pid) + TAG_HDR_SIZE;
  14. - plen += sizeof(pid) + TAG_HDR_SIZE;
  15. + if (conn->hostUniq.length) {
  16. + int len = ntohs(conn->hostUniq.length);
  17. + memcpy(cursor, &conn->hostUniq, len + TAG_HDR_SIZE);
  18. + cursor += len + TAG_HDR_SIZE;
  19. + plen += len + TAG_HDR_SIZE;
  20. }
  21. /* Copy error message */
  22. --- a/pppd/plugins/rp-pppoe/discovery.c
  23. +++ b/pppd/plugins/rp-pppoe/discovery.c
  24. @@ -80,13 +80,10 @@ static void
  25. parseForHostUniq(UINT16_t type, UINT16_t len, unsigned char *data,
  26. void *extra)
  27. {
  28. - int *val = (int *) extra;
  29. - if (type == TAG_HOST_UNIQ && len == sizeof(pid_t)) {
  30. - pid_t tmp;
  31. - memcpy(&tmp, data, len);
  32. - if (tmp == getpid()) {
  33. - *val = 1;
  34. - }
  35. + PPPoETag *tag = extra;
  36. +
  37. + if (type == TAG_HOST_UNIQ && len == ntohs(tag->length)) {
  38. + tag->length = memcmp(data, tag->payload, len);
  39. }
  40. }
  41. @@ -104,16 +101,16 @@ parseForHostUniq(UINT16_t type, UINT16_t
  42. static int
  43. packetIsForMe(PPPoEConnection *conn, PPPoEPacket *packet)
  44. {
  45. - int forMe = 0;
  46. + PPPoETag hostUniq = conn->hostUniq;
  47. /* If packet is not directed to our MAC address, forget it */
  48. if (memcmp(packet->ethHdr.h_dest, conn->myEth, ETH_ALEN)) return 0;
  49. /* If we're not using the Host-Unique tag, then accept the packet */
  50. - if (!conn->useHostUniq) return 1;
  51. + if (!conn->hostUniq.length) return 1;
  52. - parsePacket(packet, parseForHostUniq, &forMe);
  53. - return forMe;
  54. + parsePacket(packet, parseForHostUniq, &hostUniq);
  55. + return (hostUniq.length == 0);
  56. }
  57. /**********************************************************************
  58. @@ -301,16 +298,12 @@ sendPADI(PPPoEConnection *conn)
  59. }
  60. /* If we're using Host-Uniq, copy it over */
  61. - if (conn->useHostUniq) {
  62. - PPPoETag hostUniq;
  63. - pid_t pid = getpid();
  64. - hostUniq.type = htons(TAG_HOST_UNIQ);
  65. - hostUniq.length = htons(sizeof(pid));
  66. - memcpy(hostUniq.payload, &pid, sizeof(pid));
  67. - CHECK_ROOM(cursor, packet.payload, sizeof(pid) + TAG_HDR_SIZE);
  68. - memcpy(cursor, &hostUniq, sizeof(pid) + TAG_HDR_SIZE);
  69. - cursor += sizeof(pid) + TAG_HDR_SIZE;
  70. - plen += sizeof(pid) + TAG_HDR_SIZE;
  71. + if (conn->hostUniq.length) {
  72. + int len = ntohs(conn->hostUniq.length);
  73. + CHECK_ROOM(cursor, packet.payload, len + TAG_HDR_SIZE);
  74. + memcpy(cursor, &conn->hostUniq, len + TAG_HDR_SIZE);
  75. + cursor += len + TAG_HDR_SIZE;
  76. + plen += len + TAG_HDR_SIZE;
  77. }
  78. /* Add our maximum MTU/MRU */
  79. @@ -478,16 +471,12 @@ sendPADR(PPPoEConnection *conn)
  80. cursor += namelen + TAG_HDR_SIZE;
  81. /* If we're using Host-Uniq, copy it over */
  82. - if (conn->useHostUniq) {
  83. - PPPoETag hostUniq;
  84. - pid_t pid = getpid();
  85. - hostUniq.type = htons(TAG_HOST_UNIQ);
  86. - hostUniq.length = htons(sizeof(pid));
  87. - memcpy(hostUniq.payload, &pid, sizeof(pid));
  88. - CHECK_ROOM(cursor, packet.payload, sizeof(pid)+TAG_HDR_SIZE);
  89. - memcpy(cursor, &hostUniq, sizeof(pid) + TAG_HDR_SIZE);
  90. - cursor += sizeof(pid) + TAG_HDR_SIZE;
  91. - plen += sizeof(pid) + TAG_HDR_SIZE;
  92. + if (conn->hostUniq.length) {
  93. + int len = ntohs(conn->hostUniq.length);
  94. + CHECK_ROOM(cursor, packet.payload, len+TAG_HDR_SIZE);
  95. + memcpy(cursor, &conn->hostUniq, len + TAG_HDR_SIZE);
  96. + cursor += len + TAG_HDR_SIZE;
  97. + plen += len + TAG_HDR_SIZE;
  98. }
  99. /* Add our maximum MTU/MRU */
  100. --- a/pppd/plugins/rp-pppoe/plugin.c
  101. +++ b/pppd/plugins/rp-pppoe/plugin.c
  102. @@ -65,6 +65,7 @@ static char *existingSession = NULL;
  103. static int printACNames = 0;
  104. static char *pppoe_reqd_mac = NULL;
  105. unsigned char pppoe_reqd_mac_addr[6];
  106. +static char *host_uniq = NULL;
  107. static int PPPoEDevnameHook(char *cmd, char **argv, int doit);
  108. static option_t Options[] = {
  109. @@ -82,6 +83,8 @@ static option_t Options[] = {
  110. "Be verbose about discovered access concentrators"},
  111. { "pppoe-mac", o_string, &pppoe_reqd_mac,
  112. "Only connect to specified MAC address" },
  113. + { "host-uniq", o_string, &host_uniq,
  114. + "Specify custom Host-Uniq" },
  115. { NULL }
  116. };
  117. int (*OldDevnameHook)(char *cmd, char **argv, int doit) = NULL;
  118. @@ -107,7 +110,6 @@ PPPOEInitDevice(void)
  119. conn->ifName = devnam;
  120. conn->discoverySocket = -1;
  121. conn->sessionSocket = -1;
  122. - conn->useHostUniq = 1;
  123. conn->printACNames = printACNames;
  124. conn->discoveryTimeout = PADI_TIMEOUT;
  125. return 1;
  126. @@ -163,6 +165,9 @@ PPPOEConnectDevice(void)
  127. if (lcp_wantoptions[0].mru > ifr.ifr_mtu - TOTAL_OVERHEAD)
  128. lcp_wantoptions[0].mru = ifr.ifr_mtu - TOTAL_OVERHEAD;
  129. + if (host_uniq && !parseHostUniq(host_uniq, &conn->hostUniq))
  130. + fatal("Illegal value for host-uniq option");
  131. +
  132. conn->acName = acName;
  133. conn->serviceName = pppd_pppoe_service;
  134. strlcpy(ppp_devnam, devnam, sizeof(ppp_devnam));
  135. --- a/pppd/plugins/rp-pppoe/pppoe-discovery.c
  136. +++ b/pppd/plugins/rp-pppoe/pppoe-discovery.c
  137. @@ -356,7 +356,7 @@ packetIsForMe(PPPoEConnection *conn, PPP
  138. if (memcmp(packet->ethHdr.h_dest, conn->myEth, ETH_ALEN)) return 0;
  139. /* If we're not using the Host-Unique tag, then accept the packet */
  140. - if (!conn->useHostUniq) return 1;
  141. + if (!conn->hostUniq.length) return 1;
  142. parsePacket(packet, parseForHostUniq, &forMe);
  143. return forMe;
  144. @@ -494,16 +494,12 @@ sendPADI(PPPoEConnection *conn)
  145. cursor += namelen + TAG_HDR_SIZE;
  146. /* If we're using Host-Uniq, copy it over */
  147. - if (conn->useHostUniq) {
  148. - PPPoETag hostUniq;
  149. - pid_t pid = getpid();
  150. - hostUniq.type = htons(TAG_HOST_UNIQ);
  151. - hostUniq.length = htons(sizeof(pid));
  152. - memcpy(hostUniq.payload, &pid, sizeof(pid));
  153. - CHECK_ROOM(cursor, packet.payload, sizeof(pid) + TAG_HDR_SIZE);
  154. - memcpy(cursor, &hostUniq, sizeof(pid) + TAG_HDR_SIZE);
  155. - cursor += sizeof(pid) + TAG_HDR_SIZE;
  156. - plen += sizeof(pid) + TAG_HDR_SIZE;
  157. + if (conn->hostUniq.length) {
  158. + int len = ntohs(conn->hostUniq.length);
  159. + CHECK_ROOM(cursor, packet.payload, len + TAG_HDR_SIZE);
  160. + memcpy(cursor, &conn->hostUniq, len + TAG_HDR_SIZE);
  161. + cursor += len + TAG_HDR_SIZE;
  162. + plen += len + TAG_HDR_SIZE;
  163. }
  164. packet.length = htons(plen);
  165. @@ -669,7 +665,7 @@ int main(int argc, char *argv[])
  166. conn->discoveryTimeout = PADI_TIMEOUT;
  167. conn->discoveryAttempts = MAX_PADI_ATTEMPTS;
  168. - while ((opt = getopt(argc, argv, "I:D:VUQS:C:t:a:h")) > 0) {
  169. + while ((opt = getopt(argc, argv, "I:D:VUW:QS:C:t:a:h")) > 0) {
  170. switch(opt) {
  171. case 'S':
  172. conn->serviceName = xstrdup(optarg);
  173. @@ -696,7 +692,23 @@ int main(int argc, char *argv[])
  174. }
  175. break;
  176. case 'U':
  177. - conn->useHostUniq = 1;
  178. + if(conn->hostUniq.length) {
  179. + fprintf(stderr, "-U and -W are mutually exclusive\n");
  180. + exit(EXIT_FAILURE);
  181. + }
  182. + char pidbuf[5];
  183. + snprintf(pidbuf, sizeof(pidbuf), "%04x", getpid());
  184. + parseHostUniq(pidbuf, &conn->hostUniq);
  185. + break;
  186. + case 'W':
  187. + if(conn->hostUniq.length) {
  188. + fprintf(stderr, "-U and -W are mutually exclusive\n");
  189. + exit(EXIT_FAILURE);
  190. + }
  191. + if (!parseHostUniq(optarg, &conn->hostUniq)) {
  192. + fprintf(stderr, "Invalid host-uniq argument: %s\n", optarg);
  193. + exit(EXIT_FAILURE);
  194. + }
  195. break;
  196. case 'D':
  197. conn->debugFile = fopen(optarg, "w");
  198. --- a/pppd/plugins/rp-pppoe/pppoe.h
  199. +++ b/pppd/plugins/rp-pppoe/pppoe.h
  200. @@ -21,6 +21,8 @@
  201. #include <stdio.h> /* For FILE */
  202. #include <sys/types.h> /* For pid_t */
  203. +#include <ctype.h>
  204. +#include <string.h>
  205. /* How do we access raw Ethernet devices? */
  206. #undef USE_LINUX_PACKET
  207. @@ -219,7 +221,7 @@ typedef struct PPPoEConnectionStruct {
  208. char *serviceName; /* Desired service name, if any */
  209. char *acName; /* Desired AC name, if any */
  210. int synchronous; /* Use synchronous PPP */
  211. - int useHostUniq; /* Use Host-Uniq tag */
  212. + PPPoETag hostUniq; /* Use Host-Uniq tag */
  213. int printACNames; /* Just print AC names */
  214. FILE *debugFile; /* Debug file for dumping packets */
  215. int numPADOs; /* Number of PADO packets received */
  216. @@ -276,6 +278,33 @@ void pppoe_printpkt(PPPoEPacket *packet,
  217. void (*printer)(void *, char *, ...), void *arg);
  218. void pppoe_log_packet(const char *prefix, PPPoEPacket *packet);
  219. +static inline int parseHostUniq(const char *uniq, PPPoETag *tag)
  220. +{
  221. + int i, len = strlen(uniq);
  222. +
  223. +#define hex(x) \
  224. + (((x) <= '9') ? ((x) - '0') : \
  225. + (((x) <= 'F') ? ((x) - 'A' + 10) : \
  226. + ((x) - 'a' + 10)))
  227. +
  228. + if (len % 2)
  229. + return 0;
  230. +
  231. + for (i = 0; i < len; i += 2)
  232. + {
  233. + if (!isxdigit(uniq[i]) || !isxdigit(uniq[i+1]))
  234. + return 0;
  235. +
  236. + tag->payload[i / 2] = (char)(16 * hex(uniq[i]) + hex(uniq[i+1]));
  237. + }
  238. +
  239. +#undef hex
  240. +
  241. + tag->type = htons(TAG_HOST_UNIQ);
  242. + tag->length = htons(len / 2);
  243. + return 1;
  244. +}
  245. +
  246. #define SET_STRING(var, val) do { if (var) free(var); var = strDup(val); } while(0);
  247. #define CHECK_ROOM(cursor, start, len) \