test-gobex.c 32 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /*
  3. *
  4. * OBEX library with GLib integration
  5. *
  6. * Copyright (C) 2011 Intel Corporation. All rights reserved.
  7. *
  8. */
  9. #ifdef HAVE_CONFIG_H
  10. #include <config.h>
  11. #endif
  12. #include <stdlib.h>
  13. #include <sys/types.h>
  14. #include <sys/socket.h>
  15. #include <errno.h>
  16. #include <unistd.h>
  17. #include <string.h>
  18. #include <stdint.h>
  19. #include "gobex/gobex.h"
  20. #include "util.h"
  21. #define FINAL_BIT 0x80
  22. static GMainLoop *mainloop = NULL;
  23. static uint8_t pkt_connect_req[] = { G_OBEX_OP_CONNECT | FINAL_BIT,
  24. 0x00, 0x07, 0x10, 0x00, 0x10, 0x00 };
  25. static uint8_t pkt_connect_rsp[] = { 0x20 | FINAL_BIT, 0x00, 0x07,
  26. 0x10, 0x00, 0x10, 0x00 };
  27. static uint8_t pkt_disconnect_req[] = { G_OBEX_OP_DISCONNECT | FINAL_BIT,
  28. 0x00, 0x03 };
  29. static uint8_t pkt_disconnect_rsp[] = { 0x20 | FINAL_BIT, 0x00, 0x03 };
  30. static uint8_t pkt_unauth_rsp[] = { 0x41 | FINAL_BIT, 0x00, 0x1c,
  31. 0x10, 0x00, 0x10, 0x00, 0x4d, 0x00,
  32. 0x15, 0x00, 0x10, 0x00, 0x00, 0x00,
  33. 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  34. 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  35. 0x00 };
  36. static uint8_t pkt_auth_req[] = { G_OBEX_OP_CONNECT | FINAL_BIT, 0x00, 0x1c,
  37. 0x10, 0x00, 0x10, 0x00, 0x4e, 0x00,
  38. 0x15, 0x00, 0x10, 0x5a, 0xd4, 0x93,
  39. 0x93, 0xba, 0x4a, 0xf8, 0xac, 0xce,
  40. 0x7f, 0x5b, 0x1a, 0x05, 0x38, 0x74,
  41. 0x24 };
  42. static uint8_t pkt_auth_rsp[] = { 0x20 | FINAL_BIT, 0x00, 0x07,
  43. 0x10, 0x00, 0x10, 0x00 };
  44. static uint8_t pkt_setpath_req[] = { G_OBEX_OP_SETPATH | FINAL_BIT, 0x00, 0x10,
  45. 0x02, 0x00,
  46. G_OBEX_HDR_NAME, 0x00, 0x0b,
  47. 0, 'd', 0, 'i', 0, 'r', 0, 0 };
  48. static uint8_t pkt_setpath_up_req[] = { G_OBEX_OP_SETPATH | FINAL_BIT,
  49. 0x00, 0x05, 0x03, 0x00 };
  50. static uint8_t pkt_setpath_up_down_req[] = { G_OBEX_OP_SETPATH | FINAL_BIT,
  51. 0x00, 0x10, 0x03, 0x00,
  52. G_OBEX_HDR_NAME, 0x00, 0x0b,
  53. 0, 'd', 0, 'i', 0, 'r', 0, 0 };
  54. static uint8_t pkt_success_rsp[] = { 0x20 | FINAL_BIT, 0x00, 0x03 };
  55. static uint8_t pkt_mkdir_req[] = { G_OBEX_OP_SETPATH | FINAL_BIT, 0x00, 0x10,
  56. 0x00, 0x00,
  57. G_OBEX_HDR_NAME, 0x00, 0x0b,
  58. 0, 'd', 0, 'i', 0, 'r', 0, 0 };
  59. static uint8_t pkt_delete_req[] = { G_OBEX_OP_PUT | FINAL_BIT, 0x00, 0x16,
  60. G_OBEX_HDR_NAME, 0x00, 0x13,
  61. 0, 'f', 0, 'o', 0, 'o', 0, '.', 0, 't', 0, 'x', 0, 't', 0, 0 };
  62. static uint8_t pkt_copy_req[] = { G_OBEX_OP_ACTION | FINAL_BIT, 0x00, 0x1b,
  63. G_OBEX_HDR_ACTION, 0x00,
  64. G_OBEX_HDR_NAME, 0x00, 0x0b,
  65. 0, 'f', 0, 'o', 0, 'o', 0, 0,
  66. G_OBEX_HDR_DESTNAME, 0x00, 0x0b,
  67. 0, 'b', 0, 'a', 0, 'r', 0, 0 };
  68. static uint8_t pkt_move_req[] = { G_OBEX_OP_ACTION | FINAL_BIT, 0x00, 0x1b,
  69. G_OBEX_HDR_ACTION, 0x01,
  70. G_OBEX_HDR_NAME, 0x00, 0x0b,
  71. 0, 'f', 0, 'o', 0, 'o', 0, 0,
  72. G_OBEX_HDR_DESTNAME, 0x00, 0x0b,
  73. 0, 'b', 0, 'a', 0, 'r', 0, 0 };
  74. static uint8_t pkt_nval_connect_rsp[] = { 0x10 | FINAL_BIT, 0x00, 0x05,
  75. 0x10, 0x00, };
  76. static uint8_t pkt_abort_rsp[] = { 0x90, 0x00, 0x03 };
  77. static uint8_t pkt_nval_short_rsp[] = { 0x10 | FINAL_BIT, 0x12 };
  78. static uint8_t pkt_put_body[] = { G_OBEX_OP_PUT, 0x00, 0x0a,
  79. G_OBEX_HDR_BODY, 0x00, 0x07,
  80. 1, 2, 3, 4 };
  81. static gboolean timeout(gpointer user_data)
  82. {
  83. struct test_data *d = user_data;
  84. if (!g_main_loop_is_running(mainloop))
  85. return FALSE;
  86. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_TIMEOUT, "Timed out");
  87. d->timer_id = 0;
  88. g_main_loop_quit(mainloop);
  89. return FALSE;
  90. }
  91. static void connect_rsp(GObex *obex, GError *err, GObexPacket *rsp,
  92. gpointer user_data)
  93. {
  94. guint8 rsp_code;
  95. gboolean final;
  96. GError **test_err = user_data;
  97. if (err != NULL) {
  98. g_assert(*test_err == NULL);
  99. *test_err = g_error_copy(err);
  100. goto done;
  101. }
  102. rsp_code = g_obex_packet_get_operation(rsp, &final);
  103. if (rsp_code != 0x20) {
  104. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  105. "Unexpected response 0x%02x", rsp_code);
  106. goto done;
  107. }
  108. if (!final) {
  109. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  110. "Connect response didn't have final bit");
  111. goto done;
  112. }
  113. done:
  114. g_main_loop_quit(mainloop);
  115. }
  116. static void nval_connect_rsp(GObex *obex, GError *err, GObexPacket *rsp,
  117. gpointer user_data)
  118. {
  119. GError **test_err = user_data;
  120. if (!g_error_matches(err, G_OBEX_ERROR, G_OBEX_ERROR_PARSE_ERROR))
  121. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  122. "Did not get expected parse error");
  123. g_main_loop_quit(mainloop);
  124. }
  125. static void timeout_rsp(GObex *obex, GError *err, GObexPacket *rsp,
  126. gpointer user_data)
  127. {
  128. GError **test_err = user_data;
  129. if (!g_error_matches(err, G_OBEX_ERROR, G_OBEX_ERROR_TIMEOUT))
  130. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  131. "Did not get expected timeout error");
  132. g_main_loop_quit(mainloop);
  133. }
  134. static gboolean recv_and_send(GIOChannel *io, void *data, gsize len,
  135. GError **err)
  136. {
  137. gsize bytes_written, rbytes;
  138. char buf[255];
  139. GIOStatus status;
  140. status = g_io_channel_read_chars(io, buf, sizeof(buf), &rbytes, NULL);
  141. if (status != G_IO_STATUS_NORMAL) {
  142. g_set_error(err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  143. "read failed with status %d", status);
  144. return FALSE;
  145. }
  146. if (data == NULL)
  147. return TRUE;
  148. g_io_channel_write_chars(io, data, len, &bytes_written, NULL);
  149. if (bytes_written != len) {
  150. g_set_error(err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  151. "Unable to write to socket");
  152. return FALSE;
  153. }
  154. return TRUE;
  155. }
  156. static gboolean send_connect_rsp(GIOChannel *io, GIOCondition cond,
  157. gpointer user_data)
  158. {
  159. struct test_data *d = user_data;
  160. if (!recv_and_send(io, pkt_connect_rsp, sizeof(pkt_connect_rsp),
  161. &d->err))
  162. g_main_loop_quit(mainloop);
  163. d->io_id = 0;
  164. return FALSE;
  165. }
  166. static gboolean send_nval_connect_rsp(GIOChannel *io, GIOCondition cond,
  167. gpointer user_data)
  168. {
  169. struct test_data *d = user_data;
  170. if (!recv_and_send(io, pkt_nval_connect_rsp,
  171. sizeof(pkt_nval_connect_rsp), &d->err))
  172. g_main_loop_quit(mainloop);
  173. d->io_id = 0;
  174. return FALSE;
  175. }
  176. static gboolean send_nval_short_rsp(GIOChannel *io, GIOCondition cond,
  177. gpointer user_data)
  178. {
  179. struct test_data *d = user_data;
  180. if (!recv_and_send(io, pkt_nval_short_rsp,
  181. sizeof(pkt_nval_short_rsp), &d->err))
  182. g_main_loop_quit(mainloop);
  183. d->io_id = 0;
  184. return FALSE;
  185. }
  186. static gboolean send_nothing(GIOChannel *io, GIOCondition cond,
  187. gpointer user_data)
  188. {
  189. struct test_data *d = user_data;
  190. if (!recv_and_send(io, NULL, 0, &d->err))
  191. g_main_loop_quit(mainloop);
  192. d->io_id = 0;
  193. return FALSE;
  194. }
  195. static void send_req(GObexPacket *req, GObexResponseFunc rsp_func,
  196. GIOFunc send_rsp_func, int req_timeout,
  197. int transport_type)
  198. {
  199. struct test_data d;
  200. GIOChannel *io;
  201. GIOCondition cond;
  202. int test_time;
  203. GObex *obex;
  204. create_endpoints(&obex, &io, transport_type);
  205. d.err = NULL;
  206. g_obex_send_req(obex, req, req_timeout, rsp_func, &d.err, &d.err);
  207. g_assert_no_error(d.err);
  208. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  209. d.io_id = g_io_add_watch(io, cond, send_rsp_func, &d);
  210. mainloop = g_main_loop_new(NULL, FALSE);
  211. if (req_timeout > 0)
  212. test_time = req_timeout + 1;
  213. else
  214. test_time = 1;
  215. d.timer_id = g_timeout_add_seconds(test_time, timeout, &d);
  216. g_main_loop_run(mainloop);
  217. g_main_loop_unref(mainloop);
  218. mainloop = NULL;
  219. if (d.timer_id > 0)
  220. g_source_remove(d.timer_id);
  221. if (d.io_id > 0)
  222. g_source_remove(d.io_id);
  223. g_io_channel_unref(io);
  224. g_obex_unref(obex);
  225. g_assert_no_error(d.err);
  226. }
  227. static void send_connect(GObexResponseFunc rsp_func, GIOFunc send_rsp_func,
  228. int req_timeout, int transport_type)
  229. {
  230. GObexPacket *req;
  231. guint8 connect_data[] = { 0x10, 0x00, 0x10, 0x00 };
  232. req = g_obex_packet_new(G_OBEX_OP_CONNECT, TRUE, G_OBEX_HDR_INVALID);
  233. g_assert(req != NULL);
  234. g_obex_packet_set_data(req, connect_data, sizeof(connect_data),
  235. G_OBEX_DATA_REF);
  236. send_req(req, rsp_func, send_rsp_func, req_timeout, transport_type);
  237. }
  238. static void test_send_connect_req_stream(void)
  239. {
  240. send_connect(connect_rsp, send_connect_rsp, -1, SOCK_STREAM);
  241. }
  242. static void test_send_connect_req_pkt(void)
  243. {
  244. send_connect(connect_rsp, send_connect_rsp, -1, SOCK_SEQPACKET);
  245. }
  246. static void test_send_nval_connect_req_stream(void)
  247. {
  248. send_connect(nval_connect_rsp, send_nval_connect_rsp, -1, SOCK_STREAM);
  249. }
  250. static void test_send_nval_connect_req_pkt(void)
  251. {
  252. send_connect(nval_connect_rsp, send_nval_connect_rsp, -1,
  253. SOCK_SEQPACKET);
  254. }
  255. static void test_send_nval_connect_req_short_pkt(void)
  256. {
  257. send_connect(nval_connect_rsp, send_nval_short_rsp, -1,
  258. SOCK_SEQPACKET);
  259. }
  260. static void test_send_connect_req_timeout_stream(void)
  261. {
  262. send_connect(timeout_rsp, send_nothing, 0, SOCK_STREAM);
  263. }
  264. static void test_send_connect_req_timeout_pkt(void)
  265. {
  266. send_connect(timeout_rsp, send_nothing, 0, SOCK_SEQPACKET);
  267. }
  268. static void req_done(GObex *obex, GError *err, GObexPacket *rsp,
  269. gpointer user_data)
  270. {
  271. struct test_data *d = user_data;
  272. if (!g_error_matches(err, G_OBEX_ERROR, G_OBEX_ERROR_CANCELLED))
  273. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  274. "Did not get expected cancelled error");
  275. g_main_loop_quit(mainloop);
  276. }
  277. static void test_cancel_req_immediate(void)
  278. {
  279. GObexPacket *req;
  280. struct test_data d;
  281. gboolean ret;
  282. create_endpoints(&d.obex, NULL, SOCK_STREAM);
  283. d.err = NULL;
  284. req = g_obex_packet_new(G_OBEX_OP_PUT, TRUE, G_OBEX_HDR_INVALID);
  285. d.id = g_obex_send_req(d.obex, req, -1, req_done, &d, &d.err);
  286. g_assert_no_error(d.err);
  287. g_assert(d.id != 0);
  288. ret = g_obex_cancel_req(d.obex, d.id, FALSE);
  289. g_assert(ret == TRUE);
  290. mainloop = g_main_loop_new(NULL, FALSE);
  291. g_main_loop_run(mainloop);
  292. g_assert_no_error(d.err);
  293. g_obex_unref(d.obex);
  294. g_main_loop_unref(mainloop);
  295. }
  296. static gboolean cancel_server(GIOChannel *io, GIOCondition cond,
  297. gpointer user_data)
  298. {
  299. struct test_data *d = user_data;
  300. GIOStatus status;
  301. gsize bytes_written, rbytes;
  302. char buf[255];
  303. status = g_io_channel_read_chars(io, buf, sizeof(buf), &rbytes, NULL);
  304. if (status != G_IO_STATUS_NORMAL) {
  305. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  306. "Reading data failed with status %d", status);
  307. goto failed;
  308. }
  309. if (rbytes < 3) {
  310. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  311. "Not enough data from socket");
  312. goto failed;
  313. }
  314. if ((uint8_t) buf[0] == (G_OBEX_OP_PUT | FINAL_BIT)) {
  315. if (!g_obex_cancel_req(d->obex, d->id, FALSE)) {
  316. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  317. "Cancelling request failed");
  318. goto failed;
  319. }
  320. return TRUE;
  321. }
  322. if ((uint8_t) buf[0] != (G_OBEX_OP_ABORT | FINAL_BIT)) {
  323. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  324. "Neither Put nor Abort packet received");
  325. goto failed;
  326. }
  327. g_io_channel_write_chars(io, (char *) pkt_abort_rsp,
  328. sizeof(pkt_abort_rsp), &bytes_written, NULL);
  329. if (bytes_written != sizeof(pkt_abort_rsp)) {
  330. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  331. "Unable to write to socket");
  332. goto failed;
  333. }
  334. return TRUE;
  335. failed:
  336. d->io_id = 0;
  337. g_main_loop_quit(mainloop);
  338. return FALSE;
  339. }
  340. static void test_cancel_req_delay(int transport_type)
  341. {
  342. GIOChannel *io;
  343. struct test_data d;
  344. GObexPacket *req;
  345. GIOCondition cond;
  346. create_endpoints(&d.obex, &io, transport_type);
  347. d.err = NULL;
  348. req = g_obex_packet_new(G_OBEX_OP_PUT, TRUE, G_OBEX_HDR_INVALID);
  349. d.id = g_obex_send_req(d.obex, req, -1, req_done, &d, &d.err);
  350. g_assert_no_error(d.err);
  351. g_assert(d.id != 0);
  352. mainloop = g_main_loop_new(NULL, FALSE);
  353. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  354. d.io_id = g_io_add_watch(io, cond, cancel_server, &d);
  355. d.timer_id = g_timeout_add_seconds(2, timeout, &d);
  356. g_main_loop_run(mainloop);
  357. g_assert_no_error(d.err);
  358. if (d.timer_id > 0)
  359. g_source_remove(d.timer_id);
  360. if (d.io_id > 0)
  361. g_source_remove(d.io_id);
  362. g_io_channel_unref(io);
  363. g_obex_unref(d.obex);
  364. g_main_loop_unref(mainloop);
  365. }
  366. static void test_cancel_req_delay_stream(void)
  367. {
  368. test_cancel_req_delay(SOCK_STREAM);
  369. }
  370. static void test_cancel_req_delay_pkt(void)
  371. {
  372. test_cancel_req_delay(SOCK_SEQPACKET);
  373. }
  374. static gboolean rcv_data(GIOChannel *io, GIOCondition cond, gpointer user_data)
  375. {
  376. struct test_data *d = user_data;
  377. struct test_buf *b = d->recv;
  378. GIOStatus status;
  379. gsize rbytes;
  380. char buf[255];
  381. if (cond & (G_IO_HUP | G_IO_ERR | G_IO_NVAL)) {
  382. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  383. "Unexpected condition %d on socket", cond);
  384. goto done;
  385. }
  386. status = g_io_channel_read_chars(io, buf, sizeof(buf), &rbytes, NULL);
  387. if (status != G_IO_STATUS_NORMAL) {
  388. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  389. "Reading data failed with status %d", status);
  390. goto done;
  391. }
  392. if ((gssize) rbytes != b->len) {
  393. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  394. "Got %zu bytes instead of %zu",
  395. rbytes, sizeof(pkt_connect_req));
  396. dump_bufs(b->data, b->len, buf, rbytes);
  397. goto done;
  398. }
  399. if (memcmp(buf, b->data, rbytes) != 0) {
  400. g_set_error(&d->err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  401. "Mismatch with received data");
  402. dump_bufs(b->data, b->len, buf, rbytes);
  403. goto done;
  404. }
  405. done:
  406. d->io_id = 0;
  407. g_main_loop_quit(mainloop);
  408. return FALSE;
  409. }
  410. static void test_send_connect(int transport_type)
  411. {
  412. guint8 connect_data[] = { 0x10, 0x00, 0x10, 0x00 };
  413. struct test_data d;
  414. struct test_buf *b = d.recv;
  415. GIOChannel *io;
  416. GIOCondition cond;
  417. GObexPacket *req;
  418. GObex *obex;
  419. create_endpoints(&obex, &io, transport_type);
  420. memset(&d, 0, sizeof(d));
  421. b->data = pkt_connect_req;
  422. b->len = sizeof(pkt_connect_req);
  423. req = g_obex_packet_new(G_OBEX_OP_CONNECT, TRUE, G_OBEX_HDR_INVALID);
  424. g_assert(req != NULL);
  425. g_obex_packet_set_data(req, connect_data, sizeof(connect_data),
  426. G_OBEX_DATA_REF);
  427. g_obex_send(obex, req, &d.err);
  428. g_assert_no_error(d.err);
  429. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  430. d.io_id = g_io_add_watch(io, cond, rcv_data, &d);
  431. mainloop = g_main_loop_new(NULL, FALSE);
  432. d.timer_id = g_timeout_add_seconds(1, timeout, &d);
  433. g_main_loop_run(mainloop);
  434. g_main_loop_unref(mainloop);
  435. mainloop = NULL;
  436. if (d.timer_id > 0)
  437. g_source_remove(d.timer_id);
  438. if (d.io_id > 0)
  439. g_source_remove(d.io_id);
  440. g_io_channel_unref(io);
  441. g_obex_unref(obex);
  442. g_assert_no_error(d.err);
  443. }
  444. static void test_send_connect_stream(void)
  445. {
  446. test_send_connect(SOCK_STREAM);
  447. }
  448. static void test_send_connect_pkt(void)
  449. {
  450. test_send_connect(SOCK_SEQPACKET);
  451. }
  452. static void unexpected_disconn(GObex *obex, GError *err, gpointer user_data)
  453. {
  454. GError **test_err = user_data;
  455. if (!g_error_matches(err, G_OBEX_ERROR, G_OBEX_ERROR_PARSE_ERROR))
  456. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  457. "Didn't get parse error as expected");
  458. g_main_loop_quit(mainloop);
  459. }
  460. static void test_recv_unexpected(void)
  461. {
  462. struct test_data d;
  463. GObexPacket *req;
  464. GIOChannel *io;
  465. GObex *obex;
  466. guint8 buf[255];
  467. gssize len;
  468. create_endpoints(&obex, &io, SOCK_STREAM);
  469. d.err = NULL;
  470. g_obex_set_disconnect_function(obex, unexpected_disconn, &d.err);
  471. req = g_obex_packet_new(G_OBEX_RSP_CONTINUE, TRUE, G_OBEX_HDR_INVALID);
  472. len = g_obex_packet_encode(req, buf, sizeof(buf));
  473. g_obex_packet_free(req);
  474. g_assert_cmpint(len, >=, 0);
  475. g_io_channel_write_chars(io, (char *) buf, len, NULL, &d.err);
  476. g_assert_no_error(d.err);
  477. mainloop = g_main_loop_new(NULL, FALSE);
  478. d.timer_id = g_timeout_add_seconds(1, timeout, &d);
  479. g_main_loop_run(mainloop);
  480. g_main_loop_unref(mainloop);
  481. mainloop = NULL;
  482. if (d.timer_id > 0)
  483. g_source_remove(d.timer_id);
  484. g_io_channel_unref(io);
  485. g_obex_unref(obex);
  486. g_assert_no_error(d.err);
  487. }
  488. static gssize get_body_data(void *buf, gsize len, gpointer user_data)
  489. {
  490. uint8_t data[] = { 1, 2, 3, 4 };
  491. memcpy(buf, data, sizeof(data));
  492. return sizeof(data);
  493. }
  494. static gssize get_body_data_fail(void *buf, gsize len, gpointer user_data)
  495. {
  496. g_main_loop_quit(mainloop);
  497. return -1;
  498. }
  499. static void test_send_on_demand(int transport_type, GObexDataProducer func)
  500. {
  501. struct test_data d;
  502. struct test_buf *b = d.recv;
  503. GIOChannel *io;
  504. GIOCondition cond;
  505. GObexPacket *req;
  506. GObex *obex;
  507. create_endpoints(&obex, &io, transport_type);
  508. memset(&d, 0, sizeof(d));
  509. b->data = pkt_put_body;
  510. b->len = sizeof(pkt_put_body);
  511. req = g_obex_packet_new(G_OBEX_OP_PUT, FALSE, G_OBEX_HDR_INVALID);
  512. g_obex_packet_add_body(req, func, &d);
  513. g_obex_send(obex, req, &d.err);
  514. g_assert_no_error(d.err);
  515. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  516. d.io_id = g_io_add_watch(io, cond, rcv_data, &d);
  517. mainloop = g_main_loop_new(NULL, FALSE);
  518. d.timer_id = g_timeout_add_seconds(1, timeout, &d);
  519. g_main_loop_run(mainloop);
  520. g_main_loop_unref(mainloop);
  521. mainloop = NULL;
  522. if (d.timer_id > 0)
  523. g_source_remove(d.timer_id);
  524. if (d.io_id > 0)
  525. g_source_remove(d.io_id);
  526. g_io_channel_unref(io);
  527. g_obex_unref(obex);
  528. g_assert_no_error(d.err);
  529. }
  530. static void test_send_on_demand_stream(void)
  531. {
  532. test_send_on_demand(SOCK_STREAM, get_body_data);
  533. }
  534. static void test_send_on_demand_pkt(void)
  535. {
  536. test_send_on_demand(SOCK_SEQPACKET, get_body_data);
  537. }
  538. static void test_send_on_demand_fail_stream(void)
  539. {
  540. test_send_on_demand(SOCK_STREAM, get_body_data_fail);
  541. }
  542. static void test_send_on_demand_fail_pkt(void)
  543. {
  544. test_send_on_demand(SOCK_SEQPACKET, get_body_data_fail);
  545. }
  546. static void handle_connect_req(GObex *obex, GObexPacket *req,
  547. gpointer user_data)
  548. {
  549. GError **test_err = user_data;
  550. if (g_obex_packet_get_operation(req, NULL) != G_OBEX_OP_CONNECT)
  551. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  552. "Unexpected operation");
  553. g_main_loop_quit(mainloop);
  554. }
  555. static void handle_connect_err(GObex *obex, GError *err, gpointer user_data)
  556. {
  557. GError **test_err = user_data;
  558. g_main_loop_quit(mainloop);
  559. if (err != NULL)
  560. *test_err = g_error_copy(err);
  561. else
  562. *test_err = g_error_new(TEST_ERROR, TEST_ERROR_UNEXPECTED,
  563. "Disconnected");
  564. }
  565. static void recv_connect(int transport_type)
  566. {
  567. struct test_data d;
  568. GObex *obex;
  569. GIOChannel *io;
  570. GIOStatus status;
  571. gsize bytes_written;
  572. create_endpoints(&obex, &io, transport_type);
  573. d.err = NULL;
  574. g_obex_add_request_function(obex, G_OBEX_OP_CONNECT,
  575. handle_connect_req, &d.err);
  576. g_obex_set_disconnect_function(obex, handle_connect_err, &d.err);
  577. status = g_io_channel_write_chars(io, (char *) pkt_connect_req,
  578. sizeof(pkt_connect_req),
  579. &bytes_written, NULL);
  580. g_assert_cmpint(status, ==, G_IO_STATUS_NORMAL);
  581. g_assert_cmpuint(bytes_written, ==, sizeof(pkt_connect_req));
  582. mainloop = g_main_loop_new(NULL, FALSE);
  583. d.timer_id = g_timeout_add_seconds(1, timeout, &d);
  584. g_main_loop_run(mainloop);
  585. if (d.timer_id > 0)
  586. g_source_remove(d.timer_id);
  587. g_obex_unref(obex);
  588. g_io_channel_unref(io);
  589. g_main_loop_unref(mainloop);
  590. mainloop = NULL;
  591. g_assert_no_error(d.err);
  592. }
  593. static void test_recv_connect_stream(void)
  594. {
  595. recv_connect(SOCK_STREAM);
  596. }
  597. static void test_recv_connect_pkt(void)
  598. {
  599. recv_connect(SOCK_SEQPACKET);
  600. }
  601. static void disconn_ev(GObex *obex, GError *err, gpointer user_data)
  602. {
  603. GError **test_err = user_data;
  604. if (!g_error_matches(err, G_OBEX_ERROR, G_OBEX_ERROR_DISCONNECTED))
  605. g_set_error(test_err, TEST_ERROR, TEST_ERROR_UNEXPECTED,
  606. "Did not get expected disconnect error");
  607. g_main_loop_quit(mainloop);
  608. }
  609. static void test_disconnect(void)
  610. {
  611. struct test_data d;
  612. GObex *obex;
  613. GIOChannel *io;
  614. create_endpoints(&obex, &io, SOCK_STREAM);
  615. d.err = NULL;
  616. g_obex_set_disconnect_function(obex, disconn_ev, &d.err);
  617. d.timer_id = g_timeout_add_seconds(1, timeout, &d);
  618. mainloop = g_main_loop_new(NULL, FALSE);
  619. g_io_channel_shutdown(io, FALSE, NULL);
  620. g_main_loop_run(mainloop);
  621. g_assert_no_error(d.err);
  622. if (d.timer_id > 0)
  623. g_source_remove(d.timer_id);
  624. g_io_channel_unref(io);
  625. g_obex_unref(obex);
  626. g_main_loop_unref(mainloop);
  627. mainloop = NULL;
  628. }
  629. static void test_ref_unref(void)
  630. {
  631. GObex *obex;
  632. obex = create_gobex(STDIN_FILENO, G_OBEX_TRANSPORT_STREAM, FALSE);
  633. g_assert(obex != NULL);
  634. obex = g_obex_ref(obex);
  635. g_obex_unref(obex);
  636. g_obex_unref(obex);
  637. }
  638. static void test_basic(void)
  639. {
  640. GObex *obex;
  641. obex = create_gobex(STDIN_FILENO, G_OBEX_TRANSPORT_STREAM, FALSE);
  642. g_assert(obex != NULL);
  643. g_obex_unref(obex);
  644. }
  645. static void test_null_io(void)
  646. {
  647. GObex *obex;
  648. obex = g_obex_new(NULL, 0, -1, -1);
  649. g_assert(obex == NULL);
  650. }
  651. static void req_complete(GObex *obex, GError *err, GObexPacket *rsp,
  652. gpointer user_data)
  653. {
  654. struct test_data *d = user_data;
  655. if (err != NULL)
  656. d->err = g_error_copy(err);
  657. g_main_loop_quit(d->mainloop);
  658. }
  659. static void test_connect(void)
  660. {
  661. GIOChannel *io;
  662. GIOCondition cond;
  663. GObex *obex;
  664. struct test_data d = { 0, NULL, {
  665. { pkt_connect_req, sizeof(pkt_connect_req) } }, {
  666. { pkt_connect_rsp, sizeof(pkt_connect_rsp) } } };
  667. create_endpoints(&obex, &io, SOCK_STREAM);
  668. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  669. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  670. d.mainloop = g_main_loop_new(NULL, FALSE);
  671. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  672. g_obex_connect(obex, req_complete, &d, &d.err, G_OBEX_HDR_INVALID);
  673. g_assert_no_error(d.err);
  674. g_main_loop_run(d.mainloop);
  675. g_assert_cmpuint(d.count, ==, 1);
  676. g_main_loop_unref(d.mainloop);
  677. if (d.timer_id > 0)
  678. g_source_remove(d.timer_id);
  679. if (d.io_id > 0)
  680. g_source_remove(d.io_id);
  681. g_io_channel_unref(io);
  682. g_obex_unref(obex);
  683. g_assert_no_error(d.err);
  684. }
  685. static void test_obex_disconnect(void)
  686. {
  687. GIOChannel *io;
  688. GIOCondition cond;
  689. GObex *obex;
  690. struct test_data d = { 0, NULL, {
  691. { pkt_disconnect_req, sizeof(pkt_disconnect_req) } }, {
  692. { pkt_disconnect_rsp, sizeof(pkt_disconnect_rsp) } } };
  693. create_endpoints(&obex, &io, SOCK_STREAM);
  694. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  695. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  696. d.mainloop = g_main_loop_new(NULL, FALSE);
  697. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  698. g_obex_disconnect(obex, req_complete, &d, &d.err);
  699. g_assert_no_error(d.err);
  700. g_main_loop_run(d.mainloop);
  701. g_assert_cmpuint(d.count, ==, 1);
  702. g_main_loop_unref(d.mainloop);
  703. if (d.timer_id > 0)
  704. g_source_remove(d.timer_id);
  705. if (d.io_id > 0)
  706. g_source_remove(d.io_id);
  707. g_io_channel_unref(io);
  708. g_obex_unref(obex);
  709. g_assert_no_error(d.err);
  710. }
  711. static void test_auth(void)
  712. {
  713. GIOChannel *io;
  714. GIOCondition cond;
  715. GObex *obex;
  716. struct test_data d = { 0, NULL, {
  717. { pkt_connect_req, sizeof(pkt_connect_req) },
  718. { pkt_auth_req, sizeof(pkt_auth_req) } }, {
  719. { pkt_unauth_rsp, sizeof(pkt_unauth_rsp) },
  720. { pkt_auth_rsp, sizeof(pkt_auth_rsp) } },
  721. };
  722. create_endpoints(&obex, &io, SOCK_STREAM);
  723. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  724. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  725. d.mainloop = g_main_loop_new(NULL, FALSE);
  726. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  727. g_obex_connect(obex, req_complete, &d, &d.err, G_OBEX_HDR_INVALID);
  728. g_assert_no_error(d.err);
  729. g_main_loop_run(d.mainloop);
  730. g_assert_cmpuint(d.count, ==, 2);
  731. g_main_loop_unref(d.mainloop);
  732. if (d.timer_id > 0)
  733. g_source_remove(d.timer_id);
  734. if (d.io_id > 0)
  735. g_source_remove(d.io_id);
  736. g_io_channel_unref(io);
  737. g_obex_unref(obex);
  738. g_assert_no_error(d.err);
  739. }
  740. static void test_auth_fail(void)
  741. {
  742. GIOChannel *io;
  743. GIOCondition cond;
  744. GObex *obex;
  745. struct test_data d = { 0, NULL, {
  746. { pkt_connect_req, sizeof(pkt_connect_req) },
  747. { pkt_auth_req, sizeof(pkt_auth_req) } }, {
  748. { pkt_unauth_rsp, sizeof(pkt_unauth_rsp) },
  749. { pkt_unauth_rsp, sizeof(pkt_unauth_rsp) } },
  750. };
  751. create_endpoints(&obex, &io, SOCK_STREAM);
  752. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  753. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  754. d.mainloop = g_main_loop_new(NULL, FALSE);
  755. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  756. g_obex_connect(obex, req_complete, &d, &d.err, G_OBEX_HDR_INVALID);
  757. g_assert_no_error(d.err);
  758. g_main_loop_run(d.mainloop);
  759. g_assert_cmpuint(d.count, ==, 2);
  760. g_main_loop_unref(d.mainloop);
  761. if (d.timer_id > 0)
  762. g_source_remove(d.timer_id);
  763. if (d.io_id > 0)
  764. g_source_remove(d.io_id);
  765. g_io_channel_unref(io);
  766. g_obex_unref(obex);
  767. g_assert_no_error(d.err);
  768. }
  769. static void test_setpath(void)
  770. {
  771. GIOChannel *io;
  772. GIOCondition cond;
  773. GObex *obex;
  774. struct test_data d = { 0, NULL, {
  775. { pkt_setpath_req, sizeof(pkt_setpath_req) } }, {
  776. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  777. create_endpoints(&obex, &io, SOCK_STREAM);
  778. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  779. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  780. d.mainloop = g_main_loop_new(NULL, FALSE);
  781. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  782. g_obex_setpath(obex, "dir", req_complete, &d, &d.err);
  783. g_assert_no_error(d.err);
  784. g_main_loop_run(d.mainloop);
  785. g_assert_cmpuint(d.count, ==, 1);
  786. g_main_loop_unref(d.mainloop);
  787. if (d.timer_id > 0)
  788. g_source_remove(d.timer_id);
  789. if (d.io_id > 0)
  790. g_source_remove(d.io_id);
  791. g_io_channel_unref(io);
  792. g_obex_unref(obex);
  793. g_assert_no_error(d.err);
  794. }
  795. static void test_setpath_up(void)
  796. {
  797. GIOChannel *io;
  798. GIOCondition cond;
  799. GObex *obex;
  800. struct test_data d = { 0, NULL, {
  801. { pkt_setpath_up_req, sizeof(pkt_setpath_up_req) } }, {
  802. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  803. create_endpoints(&obex, &io, SOCK_STREAM);
  804. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  805. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  806. d.mainloop = g_main_loop_new(NULL, FALSE);
  807. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  808. g_obex_setpath(obex, "..", req_complete, &d, &d.err);
  809. g_assert_no_error(d.err);
  810. g_main_loop_run(d.mainloop);
  811. g_assert_cmpuint(d.count, ==, 1);
  812. g_main_loop_unref(d.mainloop);
  813. if (d.timer_id > 0)
  814. g_source_remove(d.timer_id);
  815. if (d.io_id > 0)
  816. g_source_remove(d.io_id);
  817. g_io_channel_unref(io);
  818. g_obex_unref(obex);
  819. g_assert_no_error(d.err);
  820. }
  821. static void test_setpath_up_down(void)
  822. {
  823. GIOChannel *io;
  824. GIOCondition cond;
  825. GObex *obex;
  826. struct test_data d = { 0, NULL, {
  827. { pkt_setpath_up_down_req,
  828. sizeof(pkt_setpath_up_down_req) } }, {
  829. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  830. create_endpoints(&obex, &io, SOCK_STREAM);
  831. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  832. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  833. d.mainloop = g_main_loop_new(NULL, FALSE);
  834. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  835. g_obex_setpath(obex, "../dir", req_complete, &d, &d.err);
  836. g_assert_no_error(d.err);
  837. g_main_loop_run(d.mainloop);
  838. g_assert_cmpuint(d.count, ==, 1);
  839. g_main_loop_unref(d.mainloop);
  840. if (d.timer_id > 0)
  841. g_source_remove(d.timer_id);
  842. if (d.io_id > 0)
  843. g_source_remove(d.io_id);
  844. g_io_channel_unref(io);
  845. g_obex_unref(obex);
  846. g_assert_no_error(d.err);
  847. }
  848. static void test_mkdir(void)
  849. {
  850. GIOChannel *io;
  851. GIOCondition cond;
  852. GObex *obex;
  853. struct test_data d = { 0, NULL, {
  854. { pkt_mkdir_req, sizeof(pkt_mkdir_req) } }, {
  855. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  856. create_endpoints(&obex, &io, SOCK_STREAM);
  857. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  858. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  859. d.mainloop = g_main_loop_new(NULL, FALSE);
  860. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  861. g_obex_mkdir(obex, "dir", req_complete, &d, &d.err);
  862. g_assert_no_error(d.err);
  863. g_main_loop_run(d.mainloop);
  864. g_assert_cmpuint(d.count, ==, 1);
  865. g_main_loop_unref(d.mainloop);
  866. if (d.timer_id > 0)
  867. g_source_remove(d.timer_id);
  868. if (d.io_id > 0)
  869. g_source_remove(d.io_id);
  870. g_io_channel_unref(io);
  871. g_obex_unref(obex);
  872. g_assert_no_error(d.err);
  873. }
  874. static void test_delete(void)
  875. {
  876. GIOChannel *io;
  877. GIOCondition cond;
  878. GObex *obex;
  879. struct test_data d = { 0, NULL, {
  880. { pkt_delete_req, sizeof(pkt_delete_req) } }, {
  881. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  882. create_endpoints(&obex, &io, SOCK_STREAM);
  883. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  884. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  885. d.mainloop = g_main_loop_new(NULL, FALSE);
  886. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  887. g_obex_delete(obex, "foo.txt", req_complete, &d, &d.err);
  888. g_assert_no_error(d.err);
  889. g_main_loop_run(d.mainloop);
  890. g_assert_cmpuint(d.count, ==, 1);
  891. g_main_loop_unref(d.mainloop);
  892. if (d.timer_id > 0)
  893. g_source_remove(d.timer_id);
  894. if (d.io_id > 0)
  895. g_source_remove(d.io_id);
  896. g_io_channel_unref(io);
  897. g_obex_unref(obex);
  898. g_assert_no_error(d.err);
  899. }
  900. static void test_copy(void)
  901. {
  902. GIOChannel *io;
  903. GIOCondition cond;
  904. GObex *obex;
  905. struct test_data d = { 0, NULL, {
  906. { pkt_copy_req, sizeof(pkt_copy_req) } }, {
  907. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  908. create_endpoints(&obex, &io, SOCK_STREAM);
  909. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  910. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  911. d.mainloop = g_main_loop_new(NULL, FALSE);
  912. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  913. g_obex_copy(obex, "foo", "bar", req_complete, &d, &d.err);
  914. g_assert_no_error(d.err);
  915. g_main_loop_run(d.mainloop);
  916. g_assert_cmpuint(d.count, ==, 1);
  917. g_main_loop_unref(d.mainloop);
  918. if (d.timer_id > 0)
  919. g_source_remove(d.timer_id);
  920. if (d.io_id > 0)
  921. g_source_remove(d.io_id);
  922. g_io_channel_unref(io);
  923. g_obex_unref(obex);
  924. g_assert_no_error(d.err);
  925. }
  926. static void test_move(void)
  927. {
  928. GIOChannel *io;
  929. GIOCondition cond;
  930. GObex *obex;
  931. struct test_data d = { 0, NULL, {
  932. { pkt_move_req, sizeof(pkt_move_req) } }, {
  933. { pkt_success_rsp, sizeof(pkt_success_rsp) } } };
  934. create_endpoints(&obex, &io, SOCK_STREAM);
  935. cond = G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL;
  936. d.io_id = g_io_add_watch(io, cond, test_io_cb, &d);
  937. d.mainloop = g_main_loop_new(NULL, FALSE);
  938. d.timer_id = g_timeout_add_seconds(1, test_timeout, &d);
  939. g_obex_move(obex, "foo", "bar", req_complete, &d, &d.err);
  940. g_assert_no_error(d.err);
  941. g_main_loop_run(d.mainloop);
  942. g_assert_cmpuint(d.count, ==, 1);
  943. g_main_loop_unref(d.mainloop);
  944. if (d.timer_id > 0)
  945. g_source_remove(d.timer_id);
  946. if (d.io_id > 0)
  947. g_source_remove(d.io_id);
  948. g_io_channel_unref(io);
  949. g_obex_unref(obex);
  950. g_assert_no_error(d.err);
  951. }
  952. int main(int argc, char *argv[])
  953. {
  954. g_test_init(&argc, &argv, NULL);
  955. g_test_add_func("/gobex/null_io", test_null_io);
  956. g_test_add_func("/gobex/basic", test_basic);
  957. g_test_add_func("/gobex/ref_unref", test_ref_unref);
  958. g_test_add_func("/gobex/test_disconnect", test_disconnect);
  959. g_test_add_func("/gobex/test_recv_connect_stream",
  960. test_recv_connect_stream);
  961. g_test_add_func("/gobex/test_recv_connect_pkt",
  962. test_recv_connect_pkt);
  963. g_test_add_func("/gobex/test_send_connect_stream",
  964. test_send_connect_stream);
  965. g_test_add_func("/gobex/test_send_connect_pkt",
  966. test_send_connect_pkt);
  967. g_test_add_func("/gobex/test_recv_unexpected",
  968. test_recv_unexpected);
  969. g_test_add_func("/gobex/test_send_on_demand_stream",
  970. test_send_on_demand_stream);
  971. g_test_add_func("/gobex/test_send_on_demand_pkt",
  972. test_send_on_demand_pkt);
  973. g_test_add_func("/gobex/test_send_on_demand_fail_stream",
  974. test_send_on_demand_fail_stream);
  975. g_test_add_func("/gobex/test_send_on_demand_fail_pkt",
  976. test_send_on_demand_fail_pkt);
  977. g_test_add_func("/gobex/test_send_connect_req_stream",
  978. test_send_connect_req_stream);
  979. g_test_add_func("/gobex/test_send_connect_req_pkt",
  980. test_send_connect_req_pkt);
  981. g_test_add_func("/gobex/test_send_nval_connect_req_stream",
  982. test_send_nval_connect_req_stream);
  983. g_test_add_func("/gobex/test_send_nval_connect_req_pkt",
  984. test_send_nval_connect_req_pkt);
  985. g_test_add_func("/gobex/test_send_nval_connect_req_short_pkt",
  986. test_send_nval_connect_req_short_pkt);
  987. g_test_add_func("/gobex/test_send_connect_req_timeout_stream",
  988. test_send_connect_req_timeout_stream);
  989. g_test_add_func("/gobex/test_send_connect_req_timeout_pkt",
  990. test_send_connect_req_timeout_pkt);
  991. g_test_add_func("/gobex/test_cancel_req_immediate",
  992. test_cancel_req_immediate);
  993. g_test_add_func("/gobex/test_cancel_req_delay_stream",
  994. test_cancel_req_delay_stream);
  995. g_test_add_func("/gobex/test_cancel_req_delay_pkt",
  996. test_cancel_req_delay_pkt);
  997. g_test_add_func("/gobex/test_connect", test_connect);
  998. g_test_add_func("/gobex/test_obex_disconnect", test_obex_disconnect);
  999. g_test_add_func("/gobex/test_auth", test_auth);
  1000. g_test_add_func("/gobex/test_auth_fail", test_auth_fail);
  1001. g_test_add_func("/gobex/test_setpath", test_setpath);
  1002. g_test_add_func("/gobex/test_setpath_up", test_setpath_up);
  1003. g_test_add_func("/gobex/test_setpath_up_down", test_setpath_up_down);
  1004. g_test_add_func("/gobex/test_mkdir", test_mkdir);
  1005. g_test_add_func("/gobex/test_delete", test_delete);
  1006. g_test_add_func("/gobex/test_copy", test_copy);
  1007. g_test_add_func("/gobex/test_move", test_move);
  1008. return g_test_run();
  1009. }