diff options
author | Gabor X Toth <*@tg-x.net> | 2015-05-07 12:15:58 +0000 |
---|---|---|
committer | Gabor X Toth <*@tg-x.net> | 2015-05-07 12:15:58 +0000 |
commit | 4725d59b468f1f30ba2910992333ca157682ce29 (patch) | |
tree | 23715ee20879c94a3363e28ea184370a4a71e44d /src/social | |
parent | a5edf8ac9f03a368c87ea6163994d4ac3d62af06 (diff) | |
download | gnunet-4725d59b468f1f30ba2910992333ca157682ce29.tar.gz gnunet-4725d59b468f1f30ba2910992333ca157682ce29.zip |
psyc/social: request history & state from psycstore; more documentation, tests, cleanup
Diffstat (limited to 'src/social')
-rw-r--r-- | src/social/gnunet-service-social.c | 195 | ||||
-rw-r--r-- | src/social/social_api.c | 531 | ||||
-rw-r--r-- | src/social/test_social.c | 118 |
3 files changed, 726 insertions, 118 deletions
diff --git a/src/social/gnunet-service-social.c b/src/social/gnunet-service-social.c index 9d6a8ff8f..cc71e0702 100644 --- a/src/social/gnunet-service-social.c +++ b/src/social/gnunet-service-social.c | |||
@@ -137,6 +137,8 @@ struct Place | |||
137 | struct MessageTransmitQueue *tmit_msgs_head; | 137 | struct MessageTransmitQueue *tmit_msgs_head; |
138 | struct MessageTransmitQueue *tmit_msgs_tail; | 138 | struct MessageTransmitQueue *tmit_msgs_tail; |
139 | 139 | ||
140 | struct GNUNET_PSYC_Channel *channel; | ||
141 | |||
140 | /** | 142 | /** |
141 | * Public key of the channel. | 143 | * Public key of the channel. |
142 | */ | 144 | */ |
@@ -288,6 +290,15 @@ struct Client | |||
288 | }; | 290 | }; |
289 | 291 | ||
290 | 292 | ||
293 | struct OperationClosure | ||
294 | { | ||
295 | struct GNUNET_SERVER_Client *client; | ||
296 | struct Place *plc; | ||
297 | uint64_t op_id; | ||
298 | uint32_t flags; | ||
299 | }; | ||
300 | |||
301 | |||
291 | static int | 302 | static int |
292 | psyc_transmit_message (struct Place *plc); | 303 | psyc_transmit_message (struct Place *plc); |
293 | 304 | ||
@@ -450,7 +461,7 @@ static void | |||
450 | client_send_msg (const struct Place *plc, | 461 | client_send_msg (const struct Place *plc, |
451 | const struct GNUNET_MessageHeader *msg) | 462 | const struct GNUNET_MessageHeader *msg) |
452 | { | 463 | { |
453 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 464 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
454 | "%p Sending message to clients.\n", plc); | 465 | "%p Sending message to clients.\n", plc); |
455 | 466 | ||
456 | struct ClientListItem *cli = plc->clients_head; | 467 | struct ClientListItem *cli = plc->clients_head; |
@@ -464,6 +475,46 @@ client_send_msg (const struct Place *plc, | |||
464 | 475 | ||
465 | 476 | ||
466 | /** | 477 | /** |
478 | * Send a result code back to the client. | ||
479 | * | ||
480 | * @param client | ||
481 | * Client that should receive the result code. | ||
482 | * @param result_code | ||
483 | * Code to transmit. | ||
484 | * @param op_id | ||
485 | * Operation ID in network byte order. | ||
486 | * @param data | ||
487 | * Data payload or NULL. | ||
488 | * @param data_size | ||
489 | * Size of @a data. | ||
490 | */ | ||
491 | static void | ||
492 | client_send_result (struct GNUNET_SERVER_Client *client, uint64_t op_id, | ||
493 | int64_t result_code, const void *data, uint16_t data_size) | ||
494 | { | ||
495 | struct GNUNET_OperationResultMessage *res; | ||
496 | |||
497 | res = GNUNET_malloc (sizeof (*res) + data_size); | ||
498 | res->header.type = htons (GNUNET_MESSAGE_TYPE_PSYC_RESULT_CODE); | ||
499 | res->header.size = htons (sizeof (*res) + data_size); | ||
500 | res->result_code = GNUNET_htonll_signed (result_code); | ||
501 | res->op_id = op_id; | ||
502 | if (0 < data_size) | ||
503 | memcpy (&res[1], data, data_size); | ||
504 | |||
505 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
506 | "%p Sending result to client for operation #%" PRIu64 ": " | ||
507 | "%" PRId64 " (size: %u)\n", | ||
508 | client, GNUNET_ntohll (op_id), result_code, data_size); | ||
509 | |||
510 | GNUNET_SERVER_notification_context_add (nc, client); | ||
511 | GNUNET_SERVER_notification_context_unicast (nc, client, &res->header, | ||
512 | GNUNET_NO); | ||
513 | GNUNET_free (res); | ||
514 | } | ||
515 | |||
516 | |||
517 | /** | ||
467 | * Called after a PSYC master is started. | 518 | * Called after a PSYC master is started. |
468 | */ | 519 | */ |
469 | static void | 520 | static void |
@@ -603,6 +654,7 @@ client_recv_host_enter (void *cls, struct GNUNET_SERVER_Client *client, | |||
603 | &psyc_master_started, | 654 | &psyc_master_started, |
604 | &psyc_recv_join_request, | 655 | &psyc_recv_join_request, |
605 | &psyc_recv_message, NULL, hst); | 656 | &psyc_recv_message, NULL, hst); |
657 | hst->plc.channel = GNUNET_PSYC_master_get_channel (hst->master); | ||
606 | } | 658 | } |
607 | else | 659 | else |
608 | { | 660 | { |
@@ -720,6 +772,7 @@ client_recv_guest_enter (void *cls, struct GNUNET_SERVER_Client *client, | |||
720 | &gst->origin, gst->relay_count, gst->relays, | 772 | &gst->origin, gst->relay_count, gst->relays, |
721 | &psyc_recv_message, NULL, &psyc_slave_connected, | 773 | &psyc_recv_message, NULL, &psyc_slave_connected, |
722 | &psyc_recv_join_dcsn, gst, join_msg); | 774 | &psyc_recv_join_dcsn, gst, join_msg); |
775 | gst->plc.channel = GNUNET_PSYC_slave_get_channel (gst->slave); | ||
723 | } | 776 | } |
724 | else | 777 | else |
725 | { | 778 | { |
@@ -1483,6 +1536,132 @@ client_recv_psyc_message (void *cls, struct GNUNET_SERVER_Client *client, | |||
1483 | 1536 | ||
1484 | 1537 | ||
1485 | /** | 1538 | /** |
1539 | * A historic message result arrived from PSYC. | ||
1540 | */ | ||
1541 | static void | ||
1542 | psyc_recv_history_message (void *cls, | ||
1543 | uint64_t message_id, | ||
1544 | uint32_t flags, | ||
1545 | const struct GNUNET_PSYC_MessageHeader *msg) | ||
1546 | { | ||
1547 | struct OperationClosure *opcls = cls; | ||
1548 | struct Place *plc = opcls->plc; | ||
1549 | |||
1550 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1551 | "%p Received historic message #%" PRId64 " (flags: %x)\n", | ||
1552 | plc, message_id, flags); | ||
1553 | |||
1554 | uint16_t size = ntohs (msg->header.size); | ||
1555 | |||
1556 | struct GNUNET_OperationResultMessage * | ||
1557 | res = GNUNET_malloc (sizeof (*res) + size); | ||
1558 | res->header.size = htons (sizeof (*res) + size); | ||
1559 | res->header.type = htons (GNUNET_MESSAGE_TYPE_PSYC_HISTORY_RESULT); | ||
1560 | res->op_id = opcls->op_id; | ||
1561 | res->result_code = GNUNET_htonll_signed (GNUNET_OK); | ||
1562 | |||
1563 | memcpy (&res[1], msg, size); | ||
1564 | |||
1565 | /** @todo FIXME: send only to requesting client */ | ||
1566 | client_send_msg (plc, &res->header); | ||
1567 | } | ||
1568 | |||
1569 | |||
1570 | static void | ||
1571 | psyc_recv_history_result (void *cls, int64_t result, | ||
1572 | const void *err_msg, uint16_t err_msg_size) | ||
1573 | { | ||
1574 | struct OperationClosure *opcls = cls; | ||
1575 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1576 | "%p History replay #%" PRIu64 ": " | ||
1577 | "PSYCSTORE returned %" PRId64 " (%.*s)\n", | ||
1578 | opcls->plc, GNUNET_ntohll (opcls->op_id), result, err_msg_size, err_msg); | ||
1579 | |||
1580 | // FIXME: place might have been destroyed | ||
1581 | client_send_result (opcls->client, opcls->op_id, result, err_msg, err_msg_size); | ||
1582 | } | ||
1583 | |||
1584 | |||
1585 | /** | ||
1586 | * Client requests channel history. | ||
1587 | */ | ||
1588 | static void | ||
1589 | client_recv_history_replay (void *cls, struct GNUNET_SERVER_Client *client, | ||
1590 | const struct GNUNET_MessageHeader *msg) | ||
1591 | { | ||
1592 | struct Client * | ||
1593 | ctx = GNUNET_SERVER_client_get_user_context (client, struct Client); | ||
1594 | GNUNET_assert (NULL != ctx); | ||
1595 | struct Place *plc = ctx->plc; | ||
1596 | |||
1597 | const struct GNUNET_PSYC_HistoryRequestMessage * | ||
1598 | req = (const struct GNUNET_PSYC_HistoryRequestMessage *) msg; | ||
1599 | uint16_t size = ntohs (msg->size); | ||
1600 | const char *method_prefix = (const char *) &req[1]; | ||
1601 | |||
1602 | if (size < sizeof (*req) + 1 | ||
1603 | || '\0' != method_prefix[size - sizeof (*req) - 1]) | ||
1604 | { | ||
1605 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1606 | "%p History replay #%" PRIu64 ": " | ||
1607 | "invalid method prefix. size: %u < %u?\n", | ||
1608 | plc, GNUNET_ntohll (req->op_id), size, sizeof (*req) + 1); | ||
1609 | GNUNET_break (0); | ||
1610 | GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); | ||
1611 | return; | ||
1612 | } | ||
1613 | |||
1614 | struct OperationClosure *opcls = GNUNET_malloc (sizeof (*opcls)); | ||
1615 | opcls->client = client; | ||
1616 | opcls->plc = plc; | ||
1617 | opcls->op_id = req->op_id; | ||
1618 | opcls->flags = ntohl (req->flags); | ||
1619 | |||
1620 | if (0 == req->message_limit) | ||
1621 | GNUNET_PSYC_channel_history_replay (plc->channel, | ||
1622 | GNUNET_ntohll (req->start_message_id), | ||
1623 | GNUNET_ntohll (req->end_message_id), | ||
1624 | method_prefix, opcls->flags, | ||
1625 | &psyc_recv_history_message, NULL, | ||
1626 | &psyc_recv_history_result, opcls); | ||
1627 | else | ||
1628 | GNUNET_PSYC_channel_history_replay_latest (plc->channel, | ||
1629 | GNUNET_ntohll (req->message_limit), | ||
1630 | method_prefix, opcls->flags, | ||
1631 | &psyc_recv_history_message, NULL, | ||
1632 | &psyc_recv_history_result, opcls); | ||
1633 | |||
1634 | GNUNET_SERVER_receive_done (client, GNUNET_OK); | ||
1635 | } | ||
1636 | |||
1637 | |||
1638 | static const struct GNUNET_SERVER_MessageHandler handlers[] = { | ||
1639 | { &client_recv_host_enter, NULL, | ||
1640 | GNUNET_MESSAGE_TYPE_SOCIAL_HOST_ENTER, 0 }, | ||
1641 | |||
1642 | { &client_recv_guest_enter, NULL, | ||
1643 | GNUNET_MESSAGE_TYPE_SOCIAL_GUEST_ENTER, 0 }, | ||
1644 | |||
1645 | { &client_recv_join_decision, NULL, | ||
1646 | GNUNET_MESSAGE_TYPE_PSYC_JOIN_DECISION, 0 }, | ||
1647 | |||
1648 | { &client_recv_psyc_message, NULL, | ||
1649 | GNUNET_MESSAGE_TYPE_PSYC_MESSAGE, 0 }, | ||
1650 | |||
1651 | { &client_recv_history_replay, NULL, | ||
1652 | GNUNET_MESSAGE_TYPE_PSYC_HISTORY_REPLAY, 0 }, | ||
1653 | #if FIXME | ||
1654 | { &client_recv_state_get, NULL, | ||
1655 | GNUNET_MESSAGE_TYPE_PSYC_STATE_GET, 0 }, | ||
1656 | |||
1657 | { &client_recv_state_get_prefix, NULL, | ||
1658 | GNUNET_MESSAGE_TYPE_PSYC_STATE_GET_PREFIX, 0 }, | ||
1659 | #endif | ||
1660 | { NULL, NULL, 0, 0 } | ||
1661 | }; | ||
1662 | |||
1663 | |||
1664 | /** | ||
1486 | * Initialize the PSYC service. | 1665 | * Initialize the PSYC service. |
1487 | * | 1666 | * |
1488 | * @param cls Closure. | 1667 | * @param cls Closure. |
@@ -1493,20 +1672,6 @@ static void | |||
1493 | run (void *cls, struct GNUNET_SERVER_Handle *server, | 1672 | run (void *cls, struct GNUNET_SERVER_Handle *server, |
1494 | const struct GNUNET_CONFIGURATION_Handle *c) | 1673 | const struct GNUNET_CONFIGURATION_Handle *c) |
1495 | { | 1674 | { |
1496 | static const struct GNUNET_SERVER_MessageHandler handlers[] = { | ||
1497 | { &client_recv_host_enter, NULL, | ||
1498 | GNUNET_MESSAGE_TYPE_SOCIAL_HOST_ENTER, 0 }, | ||
1499 | |||
1500 | { &client_recv_guest_enter, NULL, | ||
1501 | GNUNET_MESSAGE_TYPE_SOCIAL_GUEST_ENTER, 0 }, | ||
1502 | |||
1503 | { &client_recv_join_decision, NULL, | ||
1504 | GNUNET_MESSAGE_TYPE_PSYC_JOIN_DECISION, 0 }, | ||
1505 | |||
1506 | { &client_recv_psyc_message, NULL, | ||
1507 | GNUNET_MESSAGE_TYPE_PSYC_MESSAGE, 0 } | ||
1508 | }; | ||
1509 | |||
1510 | cfg = c; | 1675 | cfg = c; |
1511 | stats = GNUNET_STATISTICS_create ("social", cfg); | 1676 | stats = GNUNET_STATISTICS_create ("social", cfg); |
1512 | hosts = GNUNET_CONTAINER_multihashmap_create (1, GNUNET_YES); | 1677 | hosts = GNUNET_CONTAINER_multihashmap_create (1, GNUNET_YES); |
diff --git a/src/social/social_api.c b/src/social/social_api.c index afe85cbdc..559fa388e 100644 --- a/src/social/social_api.c +++ b/src/social/social_api.c | |||
@@ -47,6 +47,7 @@ static struct GNUNET_GNS_Handle *gns; | |||
47 | static struct GNUNET_NAMESTORE_Handle *namestore; | 47 | static struct GNUNET_NAMESTORE_Handle *namestore; |
48 | static struct GNUNET_PeerIdentity this_peer; | 48 | static struct GNUNET_PeerIdentity this_peer; |
49 | 49 | ||
50 | |||
50 | /** | 51 | /** |
51 | * Handle for a place where social interactions happen. | 52 | * Handle for a place where social interactions happen. |
52 | */ | 53 | */ |
@@ -239,33 +240,79 @@ struct GNUNET_SOCIAL_Announcement | |||
239 | }; | 240 | }; |
240 | 241 | ||
241 | 242 | ||
242 | struct GNUNET_SOCIAL_WatchHandle | 243 | /** |
244 | * A talk request. | ||
245 | */ | ||
246 | struct GNUNET_SOCIAL_TalkRequest | ||
243 | { | 247 | { |
244 | 248 | ||
245 | }; | 249 | }; |
246 | 250 | ||
247 | 251 | ||
248 | struct GNUNET_SOCIAL_LookHandle | 252 | struct GNUNET_SOCIAL_WatchHandle |
249 | { | 253 | { |
250 | 254 | ||
251 | }; | 255 | }; |
252 | 256 | ||
253 | 257 | ||
254 | /** | 258 | /** |
255 | * A talk request. | 259 | * A history lesson. |
256 | */ | 260 | */ |
257 | struct GNUNET_SOCIAL_TalkRequest | 261 | struct GNUNET_SOCIAL_HistoryRequest |
258 | { | 262 | { |
263 | /** | ||
264 | * Place. | ||
265 | */ | ||
266 | struct GNUNET_SOCIAL_Place *plc; | ||
259 | 267 | ||
268 | /** | ||
269 | * Operation ID. | ||
270 | */ | ||
271 | uint64_t op_id; | ||
272 | |||
273 | /** | ||
274 | * Message handler. | ||
275 | */ | ||
276 | struct GNUNET_PSYC_ReceiveHandle *recv; | ||
277 | |||
278 | /** | ||
279 | * Function to call when the operation finished. | ||
280 | */ | ||
281 | GNUNET_ResultCallback result_cb; | ||
282 | |||
283 | /** | ||
284 | * Closure for @a result_cb. | ||
285 | */ | ||
286 | void *cls; | ||
260 | }; | 287 | }; |
261 | 288 | ||
262 | 289 | ||
263 | /** | 290 | struct GNUNET_SOCIAL_LookHandle |
264 | * A history lesson. | ||
265 | */ | ||
266 | struct GNUNET_SOCIAL_HistoryLesson | ||
267 | { | 291 | { |
292 | /** | ||
293 | * Place. | ||
294 | */ | ||
295 | struct GNUNET_SOCIAL_Place *plc; | ||
296 | |||
297 | /** | ||
298 | * Operation ID. | ||
299 | */ | ||
300 | uint64_t op_id; | ||
301 | |||
302 | /** | ||
303 | * State variable result callback. | ||
304 | */ | ||
305 | GNUNET_PSYC_StateVarCallback var_cb; | ||
306 | |||
307 | /** | ||
308 | * Function to call when the operation finished. | ||
309 | */ | ||
310 | GNUNET_ResultCallback result_cb; | ||
268 | 311 | ||
312 | /** | ||
313 | * Closure for @a result_cb. | ||
314 | */ | ||
315 | void *cls; | ||
269 | }; | 316 | }; |
270 | 317 | ||
271 | 318 | ||
@@ -418,7 +465,7 @@ slicer_message (void *cls, uint64_t message_id, uint64_t fragment_offset, | |||
418 | GNUNET_assert (message_id == slicer->message_id); | 465 | GNUNET_assert (message_id == slicer->message_id); |
419 | } | 466 | } |
420 | 467 | ||
421 | LOG (GNUNET_ERROR_TYPE_WARNING, | 468 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
422 | "Slicer received message of type %u and size %u, " | 469 | "Slicer received message of type %u and size %u, " |
423 | "with ID %" PRIu64 " and method %s\n", | 470 | "with ID %" PRIu64 " and method %s\n", |
424 | ptype, ntohs (msg->size), message_id, slicer->method_name); | 471 | ptype, ntohs (msg->size), message_id, slicer->method_name); |
@@ -594,6 +641,165 @@ place_send_connect_msg (struct GNUNET_SOCIAL_Place *plc) | |||
594 | 641 | ||
595 | 642 | ||
596 | static void | 643 | static void |
644 | place_recv_result (void *cls, | ||
645 | struct GNUNET_CLIENT_MANAGER_Connection *client, | ||
646 | const struct GNUNET_MessageHeader *msg) | ||
647 | { | ||
648 | struct GNUNET_SOCIAL_Place * | ||
649 | plc = GNUNET_CLIENT_MANAGER_get_user_context_ (client, sizeof (*plc)); | ||
650 | |||
651 | const struct GNUNET_OperationResultMessage * | ||
652 | res = (const struct GNUNET_OperationResultMessage *) msg; | ||
653 | |||
654 | uint16_t size = ntohs (msg->size); | ||
655 | if (size < sizeof (*res)) | ||
656 | { /* Error, message too small. */ | ||
657 | GNUNET_break (0); | ||
658 | return; | ||
659 | } | ||
660 | |||
661 | uint16_t data_size = size - sizeof (*res); | ||
662 | const char *data = (0 < data_size) ? (const char *) &res[1] : NULL; | ||
663 | GNUNET_CLIENT_MANAGER_op_result (plc->client, GNUNET_ntohll (res->op_id), | ||
664 | GNUNET_ntohll_signed (res->result_code), | ||
665 | data, data_size); | ||
666 | } | ||
667 | |||
668 | |||
669 | static void | ||
670 | op_recv_history_result (void *cls, int64_t result, | ||
671 | const void *err_msg, uint16_t err_msg_size) | ||
672 | { | ||
673 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
674 | "Received history replay result: %" PRId64 ".\n", result); | ||
675 | |||
676 | struct GNUNET_SOCIAL_HistoryRequest *hist = cls; | ||
677 | |||
678 | if (NULL != hist->result_cb) | ||
679 | hist->result_cb (hist->cls, result, err_msg, err_msg_size); | ||
680 | |||
681 | GNUNET_PSYC_receive_destroy (hist->recv); | ||
682 | GNUNET_free (hist); | ||
683 | } | ||
684 | |||
685 | |||
686 | static void | ||
687 | op_recv_state_result (void *cls, int64_t result, | ||
688 | const void *err_msg, uint16_t err_msg_size) | ||
689 | { | ||
690 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
691 | "Received state request result: %" PRId64 ".\n", result); | ||
692 | |||
693 | struct GNUNET_SOCIAL_LookHandle *look = cls; | ||
694 | |||
695 | if (NULL != look->result_cb) | ||
696 | look->result_cb (look->cls, result, err_msg, err_msg_size); | ||
697 | |||
698 | GNUNET_free (look); | ||
699 | } | ||
700 | |||
701 | |||
702 | static void | ||
703 | place_recv_history_result (void *cls, | ||
704 | struct GNUNET_CLIENT_MANAGER_Connection *client, | ||
705 | const struct GNUNET_MessageHeader *msg) | ||
706 | { | ||
707 | struct GNUNET_SOCIAL_Place * | ||
708 | plc = GNUNET_CLIENT_MANAGER_get_user_context_ (client, sizeof (*plc)); | ||
709 | |||
710 | const struct GNUNET_OperationResultMessage * | ||
711 | res = (const struct GNUNET_OperationResultMessage *) msg; | ||
712 | struct GNUNET_PSYC_MessageHeader * | ||
713 | pmsg = (struct GNUNET_PSYC_MessageHeader *) &res[1]; | ||
714 | |||
715 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
716 | "%p Received historic fragment for message #%" PRIu64 ".\n", | ||
717 | plc, GNUNET_ntohll (pmsg->message_id)); | ||
718 | |||
719 | GNUNET_ResultCallback result_cb = NULL; | ||
720 | struct GNUNET_SOCIAL_HistoryRequest *hist = NULL; | ||
721 | |||
722 | if (GNUNET_YES != GNUNET_CLIENT_MANAGER_op_find (plc->client, | ||
723 | GNUNET_ntohll (res->op_id), | ||
724 | &result_cb, (void *) &hist)) | ||
725 | { /* Operation not found. */ | ||
726 | LOG (GNUNET_ERROR_TYPE_WARNING, | ||
727 | "%p Replay operation not found for historic fragment of message #%" | ||
728 | PRIu64 ".\n", | ||
729 | plc, GNUNET_ntohll (pmsg->message_id)); | ||
730 | return; | ||
731 | } | ||
732 | |||
733 | uint16_t size = ntohs (msg->size); | ||
734 | if (size < sizeof (*res) + sizeof (*pmsg)) | ||
735 | { /* Error, message too small. */ | ||
736 | GNUNET_break (0); | ||
737 | return; | ||
738 | } | ||
739 | |||
740 | GNUNET_PSYC_receive_message (hist->recv, | ||
741 | (const struct GNUNET_PSYC_MessageHeader *) pmsg); | ||
742 | } | ||
743 | |||
744 | |||
745 | static void | ||
746 | place_recv_state_result (void *cls, | ||
747 | struct GNUNET_CLIENT_MANAGER_Connection *client, | ||
748 | const struct GNUNET_MessageHeader *msg) | ||
749 | { | ||
750 | struct GNUNET_SOCIAL_Place * | ||
751 | plc = GNUNET_CLIENT_MANAGER_get_user_context_ (client, sizeof (*plc)); | ||
752 | |||
753 | const struct GNUNET_OperationResultMessage * | ||
754 | res = (const struct GNUNET_OperationResultMessage *) msg; | ||
755 | |||
756 | #if FIXME | ||
757 | GNUNET_ResultCallback result_cb = NULL; | ||
758 | struct GNUNET_PSYC_StateRequest *sr = NULL; | ||
759 | |||
760 | if (GNUNET_YES != GNUNET_CLIENT_MANAGER_op_find (plc->client, | ||
761 | GNUNET_ntohll (res->op_id), | ||
762 | &result_cb, (void *) &sr)) | ||
763 | { /* Operation not found. */ | ||
764 | return; | ||
765 | } | ||
766 | |||
767 | const struct GNUNET_MessageHeader * | ||
768 | modc = (struct GNUNET_MessageHeader *) &res[1]; | ||
769 | uint16_t modc_size = ntohs (modc->size); | ||
770 | if (ntohs (msg->size) - sizeof (*msg) != modc_size) | ||
771 | { | ||
772 | GNUNET_break (0); | ||
773 | return; | ||
774 | } | ||
775 | switch (ntohs (modc->type)) | ||
776 | { | ||
777 | case GNUNET_MESSAGE_TYPE_PSYC_MESSAGE_MODIFIER: | ||
778 | { | ||
779 | const struct GNUNET_PSYC_MessageModifier * | ||
780 | mod = (const struct GNUNET_PSYC_MessageModifier *) modc; | ||
781 | |||
782 | const char *name = (const char *) &mod[1]; | ||
783 | uint16_t name_size = ntohs (mod->name_size); | ||
784 | if ('\0' != name[name_size - 1]) | ||
785 | { | ||
786 | GNUNET_break (0); | ||
787 | return; | ||
788 | } | ||
789 | sr->var_cb (sr->cls, name, name + name_size, ntohs (mod->value_size)); | ||
790 | break; | ||
791 | } | ||
792 | |||
793 | case GNUNET_MESSAGE_TYPE_PSYC_MESSAGE_MOD_CONT: | ||
794 | sr->var_cb (sr->cls, NULL, (const char *) &modc[1], | ||
795 | modc_size - sizeof (*modc)); | ||
796 | break; | ||
797 | } | ||
798 | #endif | ||
799 | } | ||
800 | |||
801 | |||
802 | static void | ||
597 | place_recv_message_ack (void *cls, | 803 | place_recv_message_ack (void *cls, |
598 | struct GNUNET_CLIENT_MANAGER_Connection *client, | 804 | struct GNUNET_CLIENT_MANAGER_Connection *client, |
599 | const struct GNUNET_MessageHeader *msg) | 805 | const struct GNUNET_MessageHeader *msg) |
@@ -752,6 +958,18 @@ static struct GNUNET_CLIENT_MANAGER_MessageHandler host_handlers[] = | |||
752 | GNUNET_MESSAGE_TYPE_PSYC_MESSAGE_ACK, | 958 | GNUNET_MESSAGE_TYPE_PSYC_MESSAGE_ACK, |
753 | sizeof (struct GNUNET_MessageHeader), GNUNET_NO }, | 959 | sizeof (struct GNUNET_MessageHeader), GNUNET_NO }, |
754 | 960 | ||
961 | { &place_recv_history_result, NULL, | ||
962 | GNUNET_MESSAGE_TYPE_PSYC_HISTORY_RESULT, | ||
963 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
964 | |||
965 | { &place_recv_state_result, NULL, | ||
966 | GNUNET_MESSAGE_TYPE_PSYC_STATE_RESULT, | ||
967 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
968 | |||
969 | { &place_recv_result, NULL, | ||
970 | GNUNET_MESSAGE_TYPE_PSYC_RESULT_CODE, | ||
971 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
972 | |||
755 | { &place_recv_disconnect, NULL, 0, 0, GNUNET_NO }, | 973 | { &place_recv_disconnect, NULL, 0, 0, GNUNET_NO }, |
756 | 974 | ||
757 | { NULL, NULL, 0, 0, GNUNET_NO } | 975 | { NULL, NULL, 0, 0, GNUNET_NO } |
@@ -780,6 +998,18 @@ static struct GNUNET_CLIENT_MANAGER_MessageHandler guest_handlers[] = | |||
780 | GNUNET_MESSAGE_TYPE_PSYC_JOIN_DECISION, | 998 | GNUNET_MESSAGE_TYPE_PSYC_JOIN_DECISION, |
781 | sizeof (struct GNUNET_PSYC_JoinDecisionMessage), GNUNET_YES }, | 999 | sizeof (struct GNUNET_PSYC_JoinDecisionMessage), GNUNET_YES }, |
782 | 1000 | ||
1001 | { &place_recv_history_result, NULL, | ||
1002 | GNUNET_MESSAGE_TYPE_PSYC_HISTORY_RESULT, | ||
1003 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
1004 | |||
1005 | { &place_recv_state_result, NULL, | ||
1006 | GNUNET_MESSAGE_TYPE_PSYC_STATE_RESULT, | ||
1007 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
1008 | |||
1009 | { &place_recv_result, NULL, | ||
1010 | GNUNET_MESSAGE_TYPE_PSYC_RESULT_CODE, | ||
1011 | sizeof (struct GNUNET_OperationResultMessage), GNUNET_YES }, | ||
1012 | |||
783 | { &place_recv_disconnect, NULL, 0, 0, GNUNET_NO }, | 1013 | { &place_recv_disconnect, NULL, 0, 0, GNUNET_NO }, |
784 | 1014 | ||
785 | { NULL, NULL, 0, 0, GNUNET_NO } | 1015 | { NULL, NULL, 0, 0, GNUNET_NO } |
@@ -1546,67 +1776,13 @@ GNUNET_SOCIAL_guest_get_place (struct GNUNET_SOCIAL_Guest *gst) | |||
1546 | 1776 | ||
1547 | 1777 | ||
1548 | /** | 1778 | /** |
1549 | * A history lesson. | ||
1550 | */ | ||
1551 | struct GNUNET_SOCIAL_HistoryLesson; | ||
1552 | |||
1553 | /** | ||
1554 | * Learn about the history of a place. | ||
1555 | * | ||
1556 | * Sends messages through the slicer function of the place where | ||
1557 | * start_message_id <= message_id <= end_message_id. | ||
1558 | * The messages will have the #GNUNET_PSYC_MESSAGE_HISTORIC flag set. | ||
1559 | * | ||
1560 | * To get the latest message, use 0 for both the start and end message ID. | ||
1561 | * | ||
1562 | * @param place Place we want to learn more about. | ||
1563 | * @param start_message_id First historic message we are interested in. | ||
1564 | * @param end_message_id Last historic message we are interested in (inclusive). | ||
1565 | * @param slicer Slicer to use to process history. Can be the same as the | ||
1566 | * slicer of the place, as the HISTORIC flag allows distinguishing | ||
1567 | * old messages from fresh ones. | ||
1568 | * @param finish_cb Function called after the last message in the history lesson | ||
1569 | * is passed through the @a slicer. NULL if not needed. | ||
1570 | * @param finish_cb_cls Closure for @a finish_cb. | ||
1571 | * @return Handle to abort history lesson, never NULL (multiple lessons | ||
1572 | * at the same time are allowed). | ||
1573 | */ | ||
1574 | struct GNUNET_SOCIAL_HistoryLesson * | ||
1575 | GNUNET_SOCIAL_place_get_history (struct GNUNET_SOCIAL_Place *place, | ||
1576 | uint64_t start_message_id, | ||
1577 | uint64_t end_message_id, | ||
1578 | const struct GNUNET_SOCIAL_Slicer *slicer, | ||
1579 | void (*finish_cb)(void *), | ||
1580 | void *finish_cb_cls) | ||
1581 | { | ||
1582 | return NULL; | ||
1583 | } | ||
1584 | |||
1585 | |||
1586 | /** | ||
1587 | * Stop processing messages from the history lesson. | ||
1588 | * | ||
1589 | * Must not be called after the finish callback of the history lesson is called. | ||
1590 | * | ||
1591 | * @param hist History lesson to cancel. | ||
1592 | */ | ||
1593 | void | ||
1594 | GNUNET_SOCIAL_place_get_history_cancel (struct GNUNET_SOCIAL_HistoryLesson *hist) | ||
1595 | { | ||
1596 | |||
1597 | } | ||
1598 | |||
1599 | |||
1600 | struct GNUNET_SOCIAL_WatchHandle; | ||
1601 | |||
1602 | /** | ||
1603 | * Watch a place for changed objects. | 1779 | * Watch a place for changed objects. |
1604 | * | 1780 | * |
1605 | * @param place | 1781 | * @param place |
1606 | * Place to watch. | 1782 | * Place to watch. |
1607 | * @param object_filter | 1783 | * @param object_filter |
1608 | * Object prefix to match. | 1784 | * Object prefix to match. |
1609 | * @param state_var_cb | 1785 | * @param var_cb |
1610 | * Function to call when an object/state var changes. | 1786 | * Function to call when an object/state var changes. |
1611 | * @param cls | 1787 | * @param cls |
1612 | * Closure for callback. | 1788 | * Closure for callback. |
@@ -1616,7 +1792,7 @@ struct GNUNET_SOCIAL_WatchHandle; | |||
1616 | struct GNUNET_SOCIAL_WatchHandle * | 1792 | struct GNUNET_SOCIAL_WatchHandle * |
1617 | GNUNET_SOCIAL_place_watch (struct GNUNET_SOCIAL_Place *place, | 1793 | GNUNET_SOCIAL_place_watch (struct GNUNET_SOCIAL_Place *place, |
1618 | const char *object_filter, | 1794 | const char *object_filter, |
1619 | GNUNET_PSYC_StateVarCallback state_var_cb, | 1795 | GNUNET_PSYC_StateVarCallback var_cb, |
1620 | void *cls) | 1796 | void *cls) |
1621 | { | 1797 | { |
1622 | return NULL; | 1798 | return NULL; |
@@ -1635,45 +1811,167 @@ GNUNET_SOCIAL_place_watch_cancel (struct GNUNET_SOCIAL_WatchHandle *wh) | |||
1635 | } | 1811 | } |
1636 | 1812 | ||
1637 | 1813 | ||
1638 | struct GNUNET_SOCIAL_LookHandle; | 1814 | static struct GNUNET_SOCIAL_HistoryRequest * |
1815 | place_history_replay (struct GNUNET_SOCIAL_Place *plc, | ||
1816 | uint64_t start_message_id, | ||
1817 | uint64_t end_message_id, | ||
1818 | uint64_t message_limit, | ||
1819 | const char *method_prefix, | ||
1820 | uint32_t flags, | ||
1821 | struct GNUNET_SOCIAL_Slicer *slicer, | ||
1822 | GNUNET_ResultCallback result_cb, | ||
1823 | void *cls) | ||
1824 | { | ||
1825 | struct GNUNET_PSYC_HistoryRequestMessage *req; | ||
1826 | struct GNUNET_SOCIAL_HistoryRequest *hist = GNUNET_malloc (sizeof (*hist)); | ||
1827 | hist->plc = plc; | ||
1828 | hist->recv = GNUNET_PSYC_receive_create (NULL, &slicer_message, slicer); | ||
1829 | hist->result_cb = result_cb; | ||
1830 | hist->cls = cls; | ||
1831 | hist->op_id = GNUNET_CLIENT_MANAGER_op_add (plc->client, | ||
1832 | &op_recv_history_result, hist); | ||
1833 | |||
1834 | GNUNET_assert (NULL != method_prefix); | ||
1835 | uint16_t method_size = strnlen (method_prefix, | ||
1836 | GNUNET_SERVER_MAX_MESSAGE_SIZE | ||
1837 | - sizeof (*req)) + 1; | ||
1838 | GNUNET_assert ('\0' == method_prefix[method_size - 1]); | ||
1839 | req = GNUNET_malloc (sizeof (*req) + method_size); | ||
1840 | req->header.type = htons (GNUNET_MESSAGE_TYPE_PSYC_HISTORY_REPLAY); | ||
1841 | req->header.size = htons (sizeof (*req) + method_size); | ||
1842 | req->start_message_id = GNUNET_htonll (start_message_id); | ||
1843 | req->end_message_id = GNUNET_htonll (end_message_id); | ||
1844 | req->message_limit = GNUNET_htonll (message_limit); | ||
1845 | req->flags = htonl (flags); | ||
1846 | req->op_id = GNUNET_htonll (hist->op_id); | ||
1847 | memcpy (&req[1], method_prefix, method_size); | ||
1848 | |||
1849 | GNUNET_CLIENT_MANAGER_transmit (plc->client, &req->header); | ||
1850 | return hist; | ||
1851 | } | ||
1639 | 1852 | ||
1640 | 1853 | ||
1641 | /** | 1854 | /** |
1642 | * Look at objects in the place with a matching name prefix. | 1855 | * Learn about the history of a place. |
1856 | * | ||
1857 | * Messages are returned through the @a slicer function | ||
1858 | * and have the #GNUNET_PSYC_MESSAGE_HISTORIC flag set. | ||
1643 | * | 1859 | * |
1644 | * @param place | 1860 | * @param place |
1645 | * The place to look its objects at. | 1861 | * Place we want to learn more about. |
1646 | * @param name_prefix | 1862 | * @param start_message_id |
1647 | * Look at objects with names beginning with this value. | 1863 | * First historic message we are interested in. |
1648 | * @param state_var_cb | 1864 | * @param end_message_id |
1649 | * Function to call for each object found. | 1865 | * Last historic message we are interested in (inclusive). |
1650 | * @param cls | 1866 | * @param method_prefix |
1651 | * Closure for callback function. | 1867 | * Only retrieve messages with this method prefix. |
1868 | * @param flags | ||
1869 | * OR'ed GNUNET_PSYC_HistoryReplayFlags | ||
1870 | * @param slicer | ||
1871 | * Slicer to use for retrieved messages. | ||
1872 | * Can be the same as the slicer of the place. | ||
1873 | * @param result_cb | ||
1874 | * Function called after all messages retrieved. | ||
1875 | * NULL if not needed. | ||
1876 | * @param cls Closure for @a result_cb. | ||
1877 | */ | ||
1878 | struct GNUNET_SOCIAL_HistoryRequest * | ||
1879 | GNUNET_SOCIAL_place_history_replay (struct GNUNET_SOCIAL_Place *plc, | ||
1880 | uint64_t start_message_id, | ||
1881 | uint64_t end_message_id, | ||
1882 | const char *method_prefix, | ||
1883 | uint32_t flags, | ||
1884 | struct GNUNET_SOCIAL_Slicer *slicer, | ||
1885 | GNUNET_ResultCallback result_cb, | ||
1886 | void *cls) | ||
1887 | { | ||
1888 | return place_history_replay (plc, start_message_id, end_message_id, 0, | ||
1889 | method_prefix, flags, slicer, result_cb, cls); | ||
1890 | } | ||
1891 | |||
1892 | |||
1893 | /** | ||
1894 | * Learn about the history of a place. | ||
1652 | * | 1895 | * |
1653 | * @return Handle that can be used to stop looking at objects. | 1896 | * Sends messages through the slicer function of the place where |
1897 | * start_message_id <= message_id <= end_message_id. | ||
1898 | * The messages will have the #GNUNET_PSYC_MESSAGE_HISTORIC flag set. | ||
1899 | * | ||
1900 | * To get the latest message, use 0 for both the start and end message ID. | ||
1901 | * | ||
1902 | * @param place | ||
1903 | * Place we want to learn more about. | ||
1904 | * @param message_limit | ||
1905 | * Maximum number of historic messages we are interested in. | ||
1906 | * @param method_prefix | ||
1907 | * Only retrieve messages with this method prefix. | ||
1908 | * @param flags | ||
1909 | * OR'ed GNUNET_PSYC_HistoryReplayFlags | ||
1910 | * @param result_cb | ||
1911 | * Function called after all messages retrieved. | ||
1912 | * NULL if not needed. | ||
1913 | * @param cls Closure for @a result_cb. | ||
1654 | */ | 1914 | */ |
1655 | struct GNUNET_SOCIAL_LookHandle * | 1915 | struct GNUNET_SOCIAL_HistoryRequest * |
1656 | GNUNET_SOCIAL_place_look (struct GNUNET_SOCIAL_Place *place, | 1916 | GNUNET_SOCIAL_place_history_replay_latest (struct GNUNET_SOCIAL_Place *plc, |
1657 | const char *name_prefix, | 1917 | uint64_t message_limit, |
1658 | GNUNET_PSYC_StateVarCallback state_var_cb, | 1918 | const char *method_prefix, |
1659 | void *cls) | 1919 | uint32_t flags, |
1660 | { | 1920 | struct GNUNET_SOCIAL_Slicer *slicer, |
1661 | return NULL; | 1921 | GNUNET_ResultCallback result_cb, |
1922 | void *cls) | ||
1923 | { | ||
1924 | return place_history_replay (plc, 0, 0, message_limit, method_prefix, flags, | ||
1925 | slicer, result_cb, cls); | ||
1662 | } | 1926 | } |
1663 | 1927 | ||
1664 | 1928 | ||
1665 | /** | 1929 | /** |
1666 | * Stop looking at objects. | 1930 | * Cancel learning about the history of a place. |
1667 | * | 1931 | * |
1668 | * @param lh Look handle to stop. | 1932 | * @param hist |
1933 | * History lesson to cancel. | ||
1669 | */ | 1934 | */ |
1670 | void | 1935 | void |
1671 | GNUNET_SOCIAL_place_look_cancel (struct GNUNET_SOCIAL_LookHandle *lh) | 1936 | GNUNET_SOCIAL_place_history_replay_cancel (struct GNUNET_SOCIAL_HistoryRequest *hist) |
1672 | { | 1937 | { |
1673 | 1938 | GNUNET_PSYC_receive_destroy (hist->recv); | |
1939 | GNUNET_CLIENT_MANAGER_op_cancel (hist->plc->client, hist->op_id); | ||
1940 | GNUNET_free (hist); | ||
1674 | } | 1941 | } |
1675 | 1942 | ||
1676 | 1943 | ||
1944 | /** | ||
1945 | * Request matching state variables. | ||
1946 | */ | ||
1947 | static struct GNUNET_SOCIAL_LookHandle * | ||
1948 | place_state_get (struct GNUNET_SOCIAL_Place *plc, | ||
1949 | uint16_t type, const char *name, | ||
1950 | GNUNET_PSYC_StateVarCallback var_cb, | ||
1951 | GNUNET_ResultCallback result_cb, void *cls) | ||
1952 | { | ||
1953 | struct GNUNET_PSYC_StateRequestMessage *req; | ||
1954 | struct GNUNET_SOCIAL_LookHandle *look = GNUNET_malloc (sizeof (*look)); | ||
1955 | look->plc = plc; | ||
1956 | look->var_cb = var_cb; | ||
1957 | look->result_cb = result_cb; | ||
1958 | look->cls = cls; | ||
1959 | look->op_id = GNUNET_CLIENT_MANAGER_op_add (plc->client, | ||
1960 | &op_recv_state_result, look); | ||
1961 | |||
1962 | GNUNET_assert (NULL != name); | ||
1963 | size_t name_size = strnlen (name, GNUNET_SERVER_MAX_MESSAGE_SIZE | ||
1964 | - sizeof (*req)) + 1; | ||
1965 | req = GNUNET_malloc (sizeof (*req) + name_size); | ||
1966 | req->header.type = htons (type); | ||
1967 | req->header.size = htons (sizeof (*req) + name_size); | ||
1968 | req->op_id = GNUNET_htonll (look->op_id); | ||
1969 | memcpy (&req[1], name, name_size); | ||
1970 | |||
1971 | GNUNET_CLIENT_MANAGER_transmit (plc->client, &req->header); | ||
1972 | return look; | ||
1973 | } | ||
1974 | |||
1677 | 1975 | ||
1678 | /** | 1976 | /** |
1679 | * Look at a particular object in the place. | 1977 | * Look at a particular object in the place. |
@@ -1681,17 +1979,64 @@ GNUNET_SOCIAL_place_look_cancel (struct GNUNET_SOCIAL_LookHandle *lh) | |||
1681 | * The best matching object is returned (its name might be less specific than | 1979 | * The best matching object is returned (its name might be less specific than |
1682 | * what was requested). | 1980 | * what was requested). |
1683 | * | 1981 | * |
1684 | * @param place The place to look the object at. | 1982 | * @param place |
1685 | * @param full_name Full name of the object. | 1983 | * The place to look the object at. |
1686 | * @param value_size Set to the size of the returned value. | 1984 | * @param full_name |
1985 | * Full name of the object. | ||
1986 | * @param value_size | ||
1987 | * Set to the size of the returned value. | ||
1988 | * | ||
1687 | * @return NULL if there is no such object at this place. | 1989 | * @return NULL if there is no such object at this place. |
1688 | */ | 1990 | */ |
1689 | const void * | 1991 | struct GNUNET_SOCIAL_LookHandle * |
1690 | GNUNET_SOCIAL_place_look_at (struct GNUNET_SOCIAL_Place *place, | 1992 | GNUNET_SOCIAL_place_look_at (struct GNUNET_SOCIAL_Place *plc, |
1691 | const char *full_name, | 1993 | const char *full_name, |
1692 | size_t *value_size) | 1994 | GNUNET_PSYC_StateVarCallback var_cb, |
1995 | GNUNET_ResultCallback result_cb, | ||
1996 | void *cls) | ||
1693 | { | 1997 | { |
1694 | return NULL; | 1998 | return place_state_get (plc, GNUNET_MESSAGE_TYPE_PSYC_STATE_GET, |
1999 | full_name, var_cb, result_cb, cls); | ||
2000 | } | ||
2001 | |||
2002 | |||
2003 | /** | ||
2004 | * Look for objects in the place with a matching name prefix. | ||
2005 | * | ||
2006 | * @param place | ||
2007 | * The place to look its objects at. | ||
2008 | * @param name_prefix | ||
2009 | * Look at objects with names beginning with this value. | ||
2010 | * @param var_cb | ||
2011 | * Function to call for each object found. | ||
2012 | * @param cls | ||
2013 | * Closure for callback function. | ||
2014 | * | ||
2015 | * @return Handle that can be used to stop looking at objects. | ||
2016 | */ | ||
2017 | struct GNUNET_SOCIAL_LookHandle * | ||
2018 | GNUNET_SOCIAL_place_look_for (struct GNUNET_SOCIAL_Place *plc, | ||
2019 | const char *name_prefix, | ||
2020 | GNUNET_PSYC_StateVarCallback var_cb, | ||
2021 | GNUNET_ResultCallback result_cb, | ||
2022 | void *cls) | ||
2023 | { | ||
2024 | return place_state_get (plc, GNUNET_MESSAGE_TYPE_PSYC_STATE_GET_PREFIX, | ||
2025 | name_prefix, var_cb, result_cb, cls); | ||
2026 | } | ||
2027 | |||
2028 | |||
2029 | /** | ||
2030 | * Cancel a state request operation. | ||
2031 | * | ||
2032 | * @param sr | ||
2033 | * Handle for the operation to cancel. | ||
2034 | */ | ||
2035 | void | ||
2036 | GNUNET_SOCIAL_place_look_cancel (struct GNUNET_SOCIAL_LookHandle *look) | ||
2037 | { | ||
2038 | GNUNET_CLIENT_MANAGER_op_cancel (look->plc->client, look->op_id); | ||
2039 | GNUNET_free (look); | ||
1695 | } | 2040 | } |
1696 | 2041 | ||
1697 | 2042 | ||
diff --git a/src/social/test_social.c b/src/social/test_social.c index a1bf2940c..b18c9596c 100644 --- a/src/social/test_social.c +++ b/src/social/test_social.c | |||
@@ -75,6 +75,9 @@ struct GNUNET_SOCIAL_Slicer *guest_slicer; | |||
75 | struct GNUNET_SOCIAL_Host *hst; | 75 | struct GNUNET_SOCIAL_Host *hst; |
76 | struct GNUNET_SOCIAL_Guest *gst; | 76 | struct GNUNET_SOCIAL_Guest *gst; |
77 | 77 | ||
78 | struct GNUNET_SOCIAL_Place *hst_plc; | ||
79 | struct GNUNET_SOCIAL_Place *gst_plc; | ||
80 | |||
78 | struct GuestEnterMessage | 81 | struct GuestEnterMessage |
79 | { | 82 | { |
80 | struct GNUNET_PSYC_Message *msg; | 83 | struct GNUNET_PSYC_Message *msg; |
@@ -99,6 +102,8 @@ struct TransmitClosure | |||
99 | uint8_t join_req_count; | 102 | uint8_t join_req_count; |
100 | struct GNUNET_PSYC_Message *join_resp; | 103 | struct GNUNET_PSYC_Message *join_resp; |
101 | 104 | ||
105 | uint32_t counter; | ||
106 | |||
102 | enum | 107 | enum |
103 | { | 108 | { |
104 | TEST_NONE = 0, | 109 | TEST_NONE = 0, |
@@ -106,11 +111,15 @@ enum | |||
106 | TEST_GUEST_RECV_ENTRY_DCSN_REFUSE = 2, | 111 | TEST_GUEST_RECV_ENTRY_DCSN_REFUSE = 2, |
107 | TEST_HOST_ANSWER_DOOR_ADMIT = 3, | 112 | TEST_HOST_ANSWER_DOOR_ADMIT = 3, |
108 | TEST_GUEST_RECV_ENTRY_DCSN_ADMIT = 4, | 113 | TEST_GUEST_RECV_ENTRY_DCSN_ADMIT = 4, |
109 | TEST_HOST_ANNOUNCE = 5, | 114 | TEST_HOST_ANNOUNCE = 5, |
110 | TEST_HOST_ANNOUNCE_END = 6, | 115 | TEST_HOST_ANNOUNCE_END = 6, |
111 | TEST_GUEST_TALK = 7, | 116 | TEST_HOST_ANNOUNCE2 = 7, |
112 | TEST_GUEST_LEAVE = 8, | 117 | TEST_HOST_ANNOUNCE2_END = 8, |
113 | TEST_HOST_LEAVE = 9, | 118 | TEST_GUEST_TALK = 9, |
119 | TEST_GUEST_HISTORY_REPLAY = 10, | ||
120 | TEST_GUEST_HISTORY_REPLAY_LATEST = 11, | ||
121 | TEST_GUEST_LEAVE = 12, | ||
122 | TEST_HOST_LEAVE = 13, | ||
114 | } test; | 123 | } test; |
115 | 124 | ||
116 | 125 | ||
@@ -148,11 +157,13 @@ cleanup () | |||
148 | { | 157 | { |
149 | GNUNET_SOCIAL_guest_leave (gst, GNUNET_NO, NULL, NULL); | 158 | GNUNET_SOCIAL_guest_leave (gst, GNUNET_NO, NULL, NULL); |
150 | gst = NULL; | 159 | gst = NULL; |
160 | gst_plc = NULL; | ||
151 | } | 161 | } |
152 | if (NULL != hst) | 162 | if (NULL != hst) |
153 | { | 163 | { |
154 | GNUNET_SOCIAL_host_leave (hst, GNUNET_NO, NULL, NULL); | 164 | GNUNET_SOCIAL_host_leave (hst, GNUNET_NO, NULL, NULL); |
155 | hst = NULL; | 165 | hst = NULL; |
166 | hst_plc = NULL; | ||
156 | } | 167 | } |
157 | GNUNET_SCHEDULER_shutdown (); | 168 | GNUNET_SCHEDULER_shutdown (); |
158 | } | 169 | } |
@@ -273,6 +284,7 @@ host_left () | |||
273 | GNUNET_SOCIAL_slicer_destroy (host_slicer); | 284 | GNUNET_SOCIAL_slicer_destroy (host_slicer); |
274 | host_slicer = NULL; | 285 | host_slicer = NULL; |
275 | hst = NULL; | 286 | hst = NULL; |
287 | hst_plc = NULL; | ||
276 | 288 | ||
277 | end (); | 289 | end (); |
278 | } | 290 | } |
@@ -316,6 +328,7 @@ guest_left (void *cls) | |||
316 | GNUNET_SOCIAL_slicer_destroy (guest_slicer); | 328 | GNUNET_SOCIAL_slicer_destroy (guest_slicer); |
317 | guest_slicer = NULL; | 329 | guest_slicer = NULL; |
318 | gst = NULL; | 330 | gst = NULL; |
331 | gst_plc = NULL; | ||
319 | 332 | ||
320 | GNUNET_SCHEDULER_add_now (&schedule_host_leave, NULL); | 333 | GNUNET_SCHEDULER_add_now (&schedule_host_leave, NULL); |
321 | } | 334 | } |
@@ -331,6 +344,69 @@ guest_leave() | |||
331 | 344 | ||
332 | 345 | ||
333 | static void | 346 | static void |
347 | schedule_guest_leave (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
348 | { | ||
349 | guest_leave (); | ||
350 | } | ||
351 | |||
352 | |||
353 | static void | ||
354 | guest_recv_history_replay_latest_result (void *cls, int64_t result, | ||
355 | const void *data, uint16_t data_size) | ||
356 | { | ||
357 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
358 | "Test #%u: Guest received latest history replay result: %" PRId64 "\n" | ||
359 | "%.*s\n", | ||
360 | test, result, data_size, data); | ||
361 | GNUNET_assert (2 == counter); /* message count */ | ||
362 | GNUNET_assert (7 == result); /* fragment count */ | ||
363 | |||
364 | GNUNET_SCHEDULER_add_now (&schedule_guest_leave, NULL); | ||
365 | } | ||
366 | |||
367 | |||
368 | static void | ||
369 | guest_history_replay_latest () | ||
370 | { | ||
371 | test = TEST_GUEST_HISTORY_REPLAY_LATEST; | ||
372 | counter = 0; | ||
373 | GNUNET_SOCIAL_place_history_replay_latest (gst_plc, 3, "", | ||
374 | GNUNET_PSYC_HISTORY_REPLAY_LOCAL, | ||
375 | guest_slicer, | ||
376 | &guest_recv_history_replay_latest_result, | ||
377 | NULL); | ||
378 | } | ||
379 | |||
380 | |||
381 | static void | ||
382 | guest_recv_history_replay_result (void *cls, int64_t result, | ||
383 | const void *data, uint16_t data_size) | ||
384 | { | ||
385 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
386 | "Test #%u: Guest received history replay result: %" PRId64 "\n" | ||
387 | "%.*s\n", | ||
388 | test, result, data_size, data); | ||
389 | GNUNET_assert (2 == counter); /* message count */ | ||
390 | GNUNET_assert (7 == result); /* fragment count */ | ||
391 | |||
392 | guest_history_replay_latest (); | ||
393 | } | ||
394 | |||
395 | |||
396 | static void | ||
397 | guest_history_replay () | ||
398 | { | ||
399 | test = TEST_GUEST_HISTORY_REPLAY; | ||
400 | counter = 0; | ||
401 | GNUNET_SOCIAL_place_history_replay (gst_plc, 1, 3, "", | ||
402 | GNUNET_PSYC_HISTORY_REPLAY_LOCAL, | ||
403 | guest_slicer, | ||
404 | &guest_recv_history_replay_result, | ||
405 | NULL); | ||
406 | } | ||
407 | |||
408 | |||
409 | static void | ||
334 | guest_recv_method (void *cls, | 410 | guest_recv_method (void *cls, |
335 | const struct GNUNET_PSYC_MessageMethod *meth, | 411 | const struct GNUNET_PSYC_MessageMethod *meth, |
336 | uint64_t message_id, | 412 | uint64_t message_id, |
@@ -340,8 +416,8 @@ guest_recv_method (void *cls, | |||
340 | { | 416 | { |
341 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 417 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
342 | "Test #%u: Guest received method for message ID %" PRIu64 ":\n" | 418 | "Test #%u: Guest received method for message ID %" PRIu64 ":\n" |
343 | "%s\n", | 419 | "%s (flags: %x)\n", |
344 | test, message_id, method_name); | 420 | test, message_id, method_name, flags); |
345 | /* FIXME: check message */ | 421 | /* FIXME: check message */ |
346 | } | 422 | } |
347 | 423 | ||
@@ -395,9 +471,22 @@ guest_recv_eom (void *cls, | |||
395 | break; | 471 | break; |
396 | 472 | ||
397 | case TEST_HOST_ANNOUNCE_END: | 473 | case TEST_HOST_ANNOUNCE_END: |
474 | host_announce2 (); | ||
475 | break; | ||
476 | |||
477 | case TEST_HOST_ANNOUNCE2: | ||
478 | test = TEST_HOST_ANNOUNCE2_END; | ||
479 | break; | ||
480 | |||
481 | case TEST_HOST_ANNOUNCE2_END: | ||
398 | guest_talk (); | 482 | guest_talk (); |
399 | break; | 483 | break; |
400 | 484 | ||
485 | case TEST_GUEST_HISTORY_REPLAY: | ||
486 | case TEST_GUEST_HISTORY_REPLAY_LATEST: | ||
487 | counter++; | ||
488 | break; | ||
489 | |||
401 | default: | 490 | default: |
402 | GNUNET_assert (0); | 491 | GNUNET_assert (0); |
403 | } | 492 | } |
@@ -466,15 +555,22 @@ host_recv_eom (void *cls, | |||
466 | { | 555 | { |
467 | case TEST_HOST_ANNOUNCE: | 556 | case TEST_HOST_ANNOUNCE: |
468 | test = TEST_HOST_ANNOUNCE_END; | 557 | test = TEST_HOST_ANNOUNCE_END; |
469 | //host_announce2 (); | ||
470 | break; | 558 | break; |
471 | 559 | ||
472 | case TEST_HOST_ANNOUNCE_END: | 560 | case TEST_HOST_ANNOUNCE_END: |
561 | host_announce2 (); | ||
562 | break; | ||
563 | |||
564 | case TEST_HOST_ANNOUNCE2: | ||
565 | test = TEST_HOST_ANNOUNCE2_END; | ||
566 | break; | ||
567 | |||
568 | case TEST_HOST_ANNOUNCE2_END: | ||
473 | guest_talk (); | 569 | guest_talk (); |
474 | break; | 570 | break; |
475 | 571 | ||
476 | case TEST_GUEST_TALK: | 572 | case TEST_GUEST_TALK: |
477 | guest_leave (); | 573 | guest_history_replay (); |
478 | break; | 574 | break; |
479 | 575 | ||
480 | default: | 576 | default: |
@@ -535,7 +631,7 @@ host_announce () | |||
535 | static void | 631 | static void |
536 | host_announce2 () | 632 | host_announce2 () |
537 | { | 633 | { |
538 | test = TEST_HOST_ANNOUNCE; | 634 | test = TEST_HOST_ANNOUNCE2; |
539 | 635 | ||
540 | tmit = (struct TransmitClosure) {}; | 636 | tmit = (struct TransmitClosure) {}; |
541 | tmit.env = GNUNET_ENV_environment_create (); | 637 | tmit.env = GNUNET_ENV_environment_create (); |
@@ -667,6 +763,7 @@ guest_enter () | |||
667 | &this_peer, 0, NULL, emsg->msg, | 763 | &this_peer, 0, NULL, emsg->msg, |
668 | guest_slicer, &guest_recv_local_enter, | 764 | guest_slicer, &guest_recv_local_enter, |
669 | &guest_recv_entry_decision, NULL); | 765 | &guest_recv_entry_decision, NULL); |
766 | gst_plc = GNUNET_SOCIAL_guest_get_place (gst); | ||
670 | } | 767 | } |
671 | 768 | ||
672 | 769 | ||
@@ -727,6 +824,7 @@ id_host_ego_cb (void *cls, const struct GNUNET_IDENTITY_Ego *ego) | |||
727 | GNUNET_PSYC_CHANNEL_PRIVATE, host_slicer, | 824 | GNUNET_PSYC_CHANNEL_PRIVATE, host_slicer, |
728 | &host_entered, &host_answer_door, | 825 | &host_entered, &host_answer_door, |
729 | &host_farewell, NULL); | 826 | &host_farewell, NULL); |
827 | hst_plc = GNUNET_SOCIAL_host_get_place (hst); | ||
730 | } | 828 | } |
731 | 829 | ||
732 | 830 | ||