nbdgramconv.c 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125
  1. /*
  2. * This file is part of the UCB release of Plan 9. It is subject to the license
  3. * terms in the LICENSE file found in the top-level directory of this
  4. * distribution and at http://akaros.cs.berkeley.edu/files/Plan9License. No
  5. * part of the UCB release of Plan 9, including this file, may be copied,
  6. * modified, propagated, or distributed except according to the terms contained
  7. * in the LICENSE file.
  8. */
  9. #include <u.h>
  10. #include <libc.h>
  11. #include <ip.h>
  12. #include <thread.h>
  13. #include "netbios.h"
  14. int
  15. nbdgramconvM2S(NbDgram *s, uint8_t *ap, uint8_t *ep)
  16. {
  17. uint8_t *p = ap;
  18. int n;
  19. uint16_t length;
  20. if (ap + 6 + IPv4addrlen > ep)
  21. return 0;
  22. s->type = *p++;
  23. s->flags = *p++;
  24. s->id = nhgets(p); p+= 2;
  25. v4tov6(s->srcip, p); p+= IPv4addrlen;
  26. s->srcport = nhgets(p); p += 2;
  27. switch (s->type) {
  28. case NbDgramDirectUnique:
  29. case NbDgramDirectGroup:
  30. case NbDgramBroadcast:
  31. if (p + 4 > ep)
  32. return 0;
  33. length = nhgets(p); p += 2;
  34. s->datagram.offset = nhgets(p); p += 2;
  35. if (p + length > ep)
  36. return 0;
  37. ep = p + length;
  38. n = nbnamedecode(p, p, ep, s->datagram.srcname);
  39. if (n == 0)
  40. return 0;
  41. p += n;
  42. n = nbnamedecode(p, p, ep, s->datagram.dstname);
  43. if (n == 0)
  44. return 0;
  45. p += n;
  46. s->datagram.data = p;
  47. s->datagram.length = ep - p;
  48. p = ep;
  49. break;
  50. case NbDgramError:
  51. if (p + 1 > ep)
  52. return 0;
  53. s->error.code = *p++;
  54. break;
  55. case NbDgramQueryRequest:
  56. case NbDgramPositiveQueryResponse:
  57. case NbDgramNegativeQueryResponse:
  58. n = nbnamedecode(p, p, ep, s->query.dstname);
  59. if (n == 0)
  60. return 0;
  61. p += n;
  62. break;
  63. default:
  64. return 0;
  65. }
  66. return p - ap;
  67. }
  68. int
  69. nbdgramconvS2M(uint8_t *ap, uint8_t *ep, NbDgram *s)
  70. {
  71. uint8_t *p = ap;
  72. uint8_t *fixup;
  73. int n;
  74. if (p + 6 + IPv4addrlen > ep)
  75. return 0;
  76. *p++ = s->type;
  77. *p++ = s->flags;
  78. hnputs(p, s->id); p+= 2;
  79. v6tov4(p, s->srcip); p += IPv4addrlen;
  80. hnputs(p, s->srcport); p+= 2;
  81. switch (s->type) {
  82. case NbDgramDirectUnique:
  83. case NbDgramDirectGroup:
  84. case NbDgramBroadcast:
  85. if (p + 4 > ep)
  86. return 0;
  87. fixup = p;
  88. hnputs(p, s->datagram.length); p += 2;
  89. hnputs(p, s->datagram.offset); p += 2;
  90. n = nbnameencode(p, ep, s->datagram.srcname);
  91. if (n == 0)
  92. return 0;
  93. p += n;
  94. n = nbnameencode(p, ep, s->datagram.dstname);
  95. if (n == 0)
  96. return 0;
  97. p += n;
  98. if (p + s->datagram.length > ep)
  99. return 0;
  100. memcpy(p, s->datagram.data, s->datagram.length); p += s->datagram.length;
  101. hnputs(fixup, p - fixup - 4);
  102. break;
  103. case NbDgramError:
  104. if (p + 1 > ep)
  105. return 0;
  106. *p++ = s->error.code;
  107. break;
  108. case NbDgramQueryRequest:
  109. case NbDgramPositiveQueryResponse:
  110. case NbDgramNegativeQueryResponse:
  111. n = nbnameencode(p, ep, s->datagram.dstname);
  112. if (n == 0)
  113. return 0;
  114. p += n;
  115. break;
  116. default:
  117. return 0;
  118. }
  119. return p - ap;
  120. }