SocketStream.cpp 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. #include "SocketStream.h"
  2. using namespace bell;
  3. int SocketBuffer::open(const std::string& hostname, int port, bool isSSL) {
  4. if (internalSocket != nullptr) { close(); }
  5. if (isSSL) {
  6. internalSocket = std::make_unique<bell::TLSSocket>();
  7. } else {
  8. internalSocket = std::make_unique<bell::TCPSocket>();
  9. }
  10. internalSocket->open(hostname, port);
  11. return 0;
  12. }
  13. int SocketBuffer::close() {
  14. if (internalSocket != nullptr && isOpen()) {
  15. pubsync();
  16. internalSocket->close();
  17. internalSocket = nullptr;
  18. }
  19. return 0;
  20. }
  21. int SocketBuffer::sync() {
  22. ssize_t bw, n = pptr() - pbase();
  23. while (n > 0) {
  24. bw = internalSocket->write(reinterpret_cast<uint8_t*>(pptr() - n), n);
  25. if (bw < 0) {
  26. setp(pptr() - n, obuf + bufLen);
  27. pbump(n);
  28. return -1;
  29. }
  30. n -= bw;
  31. }
  32. setp(obuf, obuf + bufLen);
  33. return 0;
  34. }
  35. SocketBuffer::int_type SocketBuffer::underflow() {
  36. ssize_t br = internalSocket->read(reinterpret_cast<uint8_t*>(ibuf), bufLen);
  37. if (br <= 0) {
  38. setg(NULL, NULL, NULL);
  39. return traits_type::eof();
  40. }
  41. setg(ibuf, ibuf, ibuf + br);
  42. return traits_type::to_int_type(*ibuf);
  43. }
  44. SocketBuffer::int_type SocketBuffer::overflow(int_type c) {
  45. if (sync() < 0)
  46. return traits_type::eof();
  47. if (traits_type::eq_int_type(c, traits_type::eof()))
  48. return traits_type::not_eof(c);
  49. *pptr() = traits_type::to_char_type(c);
  50. pbump(1);
  51. return c;
  52. }
  53. std::streamsize SocketBuffer::xsgetn(char_type* __s, std::streamsize __n) {
  54. const std::streamsize bn = egptr() - gptr();
  55. if (__n <= bn) {
  56. traits_type::copy(__s, gptr(), __n);
  57. gbump(__n);
  58. return __n;
  59. }
  60. traits_type::copy(__s, gptr(), bn);
  61. setg(NULL, NULL, NULL);
  62. std::streamsize remain = __n - bn;
  63. char_type* end = __s + __n;
  64. ssize_t br;
  65. while (remain > 0) {
  66. br = internalSocket->read(reinterpret_cast<uint8_t*>(end - remain), remain);
  67. if (br <= 0)
  68. return (__n - remain);
  69. remain -= br;
  70. }
  71. return __n;
  72. }
  73. std::streamsize SocketBuffer::xsputn(const char_type* __s,
  74. std::streamsize __n) {
  75. if (pptr() + __n <= epptr()) {
  76. traits_type::copy(pptr(), __s, __n);
  77. pbump(__n);
  78. return __n;
  79. }
  80. if (sync() < 0)
  81. return 0;
  82. ssize_t bw;
  83. std::streamsize remain = __n;
  84. const char_type* end = __s + __n;
  85. while (remain > bufLen) {
  86. bw = internalSocket->write((uint8_t*)(end - remain), remain);
  87. if (bw < 0)
  88. return (__n - remain);
  89. remain -= bw;
  90. }
  91. if (remain > 0) {
  92. traits_type::copy(pptr(), end - remain, remain);
  93. pbump(remain);
  94. }
  95. return __n;
  96. }