aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorlurchi <lurchi@strangeplace.net>2017-08-21 01:07:27 +0200
committerlurchi <lurchi@strangeplace.net>2017-08-21 01:07:27 +0200
commit024beb50aadb8e5a58dbb85cd3e819748dd4de3e (patch)
tree3f09974289476997c5af64975a20e5f0018d9c16 /src
parente29921e503d8da33f0b9b15302288c5572ec9bf4 (diff)
downloadgnunet-024beb50aadb8e5a58dbb85cd3e819748dd4de3e.tar.gz
gnunet-024beb50aadb8e5a58dbb85cd3e819748dd4de3e.zip
only allocate network / file handles and store them in the task when GNUNET_SCHEDULER_add_select is used
Diffstat (limited to 'src')
-rw-r--r--src/util/scheduler.c194
1 files changed, 78 insertions, 116 deletions
diff --git a/src/util/scheduler.c b/src/util/scheduler.c
index 33aba9ad6..71a3bd956 100644
--- a/src/util/scheduler.c
+++ b/src/util/scheduler.c
@@ -117,21 +117,6 @@ struct GNUNET_SCHEDULER_Task
117 */ 117 */
118 void *callback_cls; 118 void *callback_cls;
119 119
120 ///**
121 // * Set of file descriptors this task is waiting
122 // * for for reading. Once ready, this is updated
123 // * to reflect the set of file descriptors ready
124 // * for operation.
125 // */
126 //struct GNUNET_NETWORK_FDSet *read_set;
127
128 ///**
129 // * Set of file descriptors this task is waiting for for writing.
130 // * Once ready, this is updated to reflect the set of file
131 // * descriptors ready for operation.
132 // */
133 //struct GNUNET_NETWORK_FDSet *write_set;
134
135 /** 120 /**
136 * Information about which FDs are ready for this task (and why). 121 * Information about which FDs are ready for this task (and why).
137 */ 122 */
@@ -145,11 +130,6 @@ struct GNUNET_SCHEDULER_Task
145 struct GNUNET_SCHEDULER_FdInfo fdx; 130 struct GNUNET_SCHEDULER_FdInfo fdx;
146 131
147 /** 132 /**
148 * Absolute timeout value for the task, or
149 * #GNUNET_TIME_UNIT_FOREVER_ABS for "no timeout".
150 */
151
152 /**
153 * Size of the @e fds array. 133 * Size of the @e fds array.
154 */ 134 */
155 unsigned int fds_len; 135 unsigned int fds_len;
@@ -166,6 +146,17 @@ struct GNUNET_SCHEDULER_Task
166 */ 146 */
167 unsigned int ready_fds_len; 147 unsigned int ready_fds_len;
168 148
149 /**
150 * Do we own the network and file handlers referenced by the FdInfo
151 * structs in the fds array. This will only be GNUNET_YES if the
152 * task was created by the #GNUNET_SCHEDULER_add_select function.
153 */
154 int own_handlers;
155
156 /**
157 * Absolute timeout value for the task, or
158 * #GNUNET_TIME_UNIT_FOREVER_ABS for "no timeout".
159 */
169 struct GNUNET_TIME_Absolute timeout; 160 struct GNUNET_TIME_Absolute timeout;
170 161
171#if PROFILE_DELAYS 162#if PROFILE_DELAYS
@@ -489,29 +480,6 @@ GNUNET_SCHEDULER_shutdown ()
489} 480}
490 481
491 482
492static void
493destroy_fd_info_list (struct GNUNET_SCHEDULER_FdInfo *fds, unsigned int fds_len)
494{
495 unsigned int i;
496 for (i = 0; i != fds_len; ++i)
497 {
498 const struct GNUNET_SCHEDULER_FdInfo *fdi = fds + i;
499 if (fdi->fd)
500 {
501 GNUNET_NETWORK_socket_free_memory_only_ ((struct GNUNET_NETWORK_Handle *) fdi->fd);
502 }
503 if (fdi->fh)
504 {
505 // FIXME: on WIN32 this is not enough! A function
506 // GNUNET_DISK_file_free_memory_only would be nice
507 GNUNET_free ((void *) fdi->fh);
508 }
509 }
510 /* free the array */
511 GNUNET_array_grow (fds, fds_len, 0);
512}
513
514
515/** 483/**
516 * Destroy a task (release associated resources) 484 * Destroy a task (release associated resources)
517 * 485 *
@@ -520,15 +488,33 @@ destroy_fd_info_list (struct GNUNET_SCHEDULER_FdInfo *fds, unsigned int fds_len)
520static void 488static void
521destroy_task (struct GNUNET_SCHEDULER_Task *t) 489destroy_task (struct GNUNET_SCHEDULER_Task *t)
522{ 490{
491 unsigned int i;
492
493 if (GNUNET_YES == t->own_handlers)
494 {
495 for (i = 0; i != t->fds_len; ++i)
496 {
497 const struct GNUNET_NETWORK_Handle *fd = t->fds[i].fd;
498 const struct GNUNET_DISK_FileHandle *fh = t->fds[i].fh;
499 if (fd)
500 {
501 GNUNET_NETWORK_socket_free_memory_only_ ((struct GNUNET_NETWORK_Handle *) fd);
502 }
503 if (fh)
504 {
505 // FIXME: on WIN32 this is not enough! A function
506 // GNUNET_DISK_file_free_memory_only would be nice
507 GNUNET_free ((void *) fh);
508 }
509 }
510 }
523 if (t->fds_len > 1) 511 if (t->fds_len > 1)
524 { 512 {
525 destroy_fd_info_list ((struct GNUNET_SCHEDULER_FdInfo *) t->fds, 513 GNUNET_array_grow (t->fds, t->fds_len, 0);
526 t->fds_len);
527 } 514 }
528 if (t->ready_fds_len > 0) 515 if (t->ready_fds_len > 0)
529 { 516 {
530 destroy_fd_info_list ((struct GNUNET_SCHEDULER_FdInfo *) t->ready_fds, 517 GNUNET_array_grow (t->ready_fds, t->ready_fds_len, 0);
531 t->ready_fds_len);
532 } 518 }
533#if EXECINFO 519#if EXECINFO
534 GNUNET_free (t->backtrace_strings); 520 GNUNET_free (t->backtrace_strings);
@@ -737,13 +723,13 @@ GNUNET_SCHEDULER_get_load (enum GNUNET_SCHEDULER_Priority p)
737void 723void
738init_fd_info (struct GNUNET_SCHEDULER_Task *t, 724init_fd_info (struct GNUNET_SCHEDULER_Task *t,
739 const struct GNUNET_NETWORK_Handle *const *read_nh, 725 const struct GNUNET_NETWORK_Handle *const *read_nh,
740 size_t read_nh_len, 726 unsigned int read_nh_len,
741 const struct GNUNET_NETWORK_Handle *const *write_nh, 727 const struct GNUNET_NETWORK_Handle *const *write_nh,
742 size_t write_nh_len, 728 unsigned int write_nh_len,
743 const struct GNUNET_DISK_FileHandle *const *read_fh, 729 const struct GNUNET_DISK_FileHandle *const *read_fh,
744 size_t read_fh_len, 730 unsigned int read_fh_len,
745 const struct GNUNET_DISK_FileHandle *const *write_fh, 731 const struct GNUNET_DISK_FileHandle *const *write_fh,
746 size_t write_fh_len) 732 unsigned int write_fh_len)
747{ 733{
748 struct GNUNET_SCHEDULER_FdInfo *fdi; 734 struct GNUNET_SCHEDULER_FdInfo *fdi;
749 735
@@ -754,7 +740,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
754 t->fds = fdi; 740 t->fds = fdi;
755 if (1 == read_nh_len) 741 if (1 == read_nh_len)
756 { 742 {
757 fdi->fd = GNUNET_NETWORK_socket_box_native (GNUNET_NETWORK_get_fd (*read_nh)); 743 fdi->fd = *read_nh;
758 GNUNET_assert (NULL != fdi->fd); 744 GNUNET_assert (NULL != fdi->fd);
759 fdi->et = GNUNET_SCHEDULER_ET_IN; 745 fdi->et = GNUNET_SCHEDULER_ET_IN;
760 fdi->sock = GNUNET_NETWORK_get_fd (*read_nh); 746 fdi->sock = GNUNET_NETWORK_get_fd (*read_nh);
@@ -763,7 +749,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
763 } 749 }
764 else if (1 == write_nh_len) 750 else if (1 == write_nh_len)
765 { 751 {
766 fdi->fd = GNUNET_NETWORK_socket_box_native (GNUNET_NETWORK_get_fd (*write_nh)); 752 fdi->fd = *write_nh;
767 GNUNET_assert (NULL != fdi->fd); 753 GNUNET_assert (NULL != fdi->fd);
768 fdi->et = GNUNET_SCHEDULER_ET_OUT; 754 fdi->et = GNUNET_SCHEDULER_ET_OUT;
769 fdi->sock = GNUNET_NETWORK_get_fd (*write_nh); 755 fdi->sock = GNUNET_NETWORK_get_fd (*write_nh);
@@ -772,7 +758,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
772 } 758 }
773 else if (1 == read_fh_len) 759 else if (1 == read_fh_len)
774 { 760 {
775 fdi->fh = GNUNET_DISK_get_handle_from_int_fd ((*read_fh)->fd); 761 fdi->fh = *read_fh;
776 GNUNET_assert (NULL != fdi->fh); 762 GNUNET_assert (NULL != fdi->fh);
777 fdi->et = GNUNET_SCHEDULER_ET_IN; 763 fdi->et = GNUNET_SCHEDULER_ET_IN;
778 fdi->sock = (*read_fh)->fd; // FIXME: does not work under WIN32 764 fdi->sock = (*read_fh)->fd; // FIXME: does not work under WIN32
@@ -781,7 +767,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
781 } 767 }
782 else 768 else
783 { 769 {
784 fdi->fh = GNUNET_DISK_get_handle_from_int_fd ((*write_fh)->fd); 770 fdi->fh = *write_fh;
785 GNUNET_assert (NULL != fdi->fh); 771 GNUNET_assert (NULL != fdi->fh);
786 fdi->et = GNUNET_SCHEDULER_ET_OUT; 772 fdi->et = GNUNET_SCHEDULER_ET_OUT;
787 fdi->sock = (*write_fh)->fd; // FIXME: does not work under WIN32 773 fdi->sock = (*write_fh)->fd; // FIXME: does not work under WIN32
@@ -795,10 +781,10 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
795 t->fds = fdi; 781 t->fds = fdi;
796 t->read_fd = -1; 782 t->read_fd = -1;
797 t->write_fd = -1; 783 t->write_fd = -1;
798 size_t i; 784 unsigned int i;
799 for (i = 0; i != read_nh_len; ++i) 785 for (i = 0; i != read_nh_len; ++i)
800 { 786 {
801 fdi->fd = GNUNET_NETWORK_socket_box_native (GNUNET_NETWORK_get_fd (read_nh[i])); 787 fdi->fd = read_nh[i];
802 GNUNET_assert (NULL != fdi->fd); 788 GNUNET_assert (NULL != fdi->fd);
803 fdi->et = GNUNET_SCHEDULER_ET_IN; 789 fdi->et = GNUNET_SCHEDULER_ET_IN;
804 fdi->sock = GNUNET_NETWORK_get_fd (read_nh[i]); 790 fdi->sock = GNUNET_NETWORK_get_fd (read_nh[i]);
@@ -806,7 +792,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
806 } 792 }
807 for (i = 0; i != write_nh_len; ++i) 793 for (i = 0; i != write_nh_len; ++i)
808 { 794 {
809 fdi->fd = GNUNET_NETWORK_socket_box_native (GNUNET_NETWORK_get_fd (write_nh[i])); 795 fdi->fd = write_nh[i];
810 GNUNET_assert (NULL != fdi->fd); 796 GNUNET_assert (NULL != fdi->fd);
811 fdi->et = GNUNET_SCHEDULER_ET_OUT; 797 fdi->et = GNUNET_SCHEDULER_ET_OUT;
812 fdi->sock = GNUNET_NETWORK_get_fd (write_nh[i]); 798 fdi->sock = GNUNET_NETWORK_get_fd (write_nh[i]);
@@ -814,7 +800,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
814 } 800 }
815 for (i = 0; i != read_fh_len; ++i) 801 for (i = 0; i != read_fh_len; ++i)
816 { 802 {
817 fdi->fh = GNUNET_DISK_get_handle_from_int_fd (read_fh[i]->fd); 803 fdi->fh = read_fh[i];
818 GNUNET_assert (NULL != fdi->fh); 804 GNUNET_assert (NULL != fdi->fh);
819 fdi->et = GNUNET_SCHEDULER_ET_IN; 805 fdi->et = GNUNET_SCHEDULER_ET_IN;
820 fdi->sock = (read_fh[i])->fd; // FIXME: does not work under WIN32 806 fdi->sock = (read_fh[i])->fd; // FIXME: does not work under WIN32
@@ -822,7 +808,7 @@ init_fd_info (struct GNUNET_SCHEDULER_Task *t,
822 } 808 }
823 for (i = 0; i != write_fh_len; ++i) 809 for (i = 0; i != write_fh_len; ++i)
824 { 810 {
825 fdi->fh = GNUNET_DISK_get_handle_from_int_fd (write_fh[i]->fd); 811 fdi->fh = write_fh[i];
826 GNUNET_assert (NULL != fdi->fh); 812 GNUNET_assert (NULL != fdi->fh);
827 fdi->et = GNUNET_SCHEDULER_ET_OUT; 813 fdi->et = GNUNET_SCHEDULER_ET_OUT;
828 fdi->sock = (write_fh[i])->fd; // FIXME: does not work under WIN32 814 fdi->sock = (write_fh[i])->fd; // FIXME: does not work under WIN32
@@ -891,10 +877,6 @@ GNUNET_SCHEDULER_cancel (struct GNUNET_SCHEDULER_Task *task)
891 (GNUNET_NO == task->lifeness) ); 877 (GNUNET_NO == task->lifeness) );
892 if (! task->in_ready_list) 878 if (! task->in_ready_list)
893 { 879 {
894 //if ( (-1 == task->read_fd) &&
895 // (-1 == task->write_fd) &&
896 // (NULL == task->read_set) &&
897 // (NULL == task->write_set) )
898 if (NULL == task->fds) 880 if (NULL == task->fds)
899 { 881 {
900 if (GNUNET_YES == task->on_shutdown) 882 if (GNUNET_YES == task->on_shutdown)
@@ -1637,7 +1619,8 @@ GNUNET_SCHEDULER_add_file_with_priority (struct GNUNET_TIME_Relative delay,
1637 1619
1638 1620
1639int 1621int
1640extract_handles (const struct GNUNET_NETWORK_FDSet *fdset, 1622extract_handles (struct GNUNET_SCHEDULER_Task *t,
1623 const struct GNUNET_NETWORK_FDSet *fdset,
1641 const struct GNUNET_NETWORK_Handle ***ntarget, 1624 const struct GNUNET_NETWORK_Handle ***ntarget,
1642 unsigned int *extracted_nhandles, 1625 unsigned int *extracted_nhandles,
1643 const struct GNUNET_DISK_FileHandle ***ftarget, 1626 const struct GNUNET_DISK_FileHandle ***ftarget,
@@ -1647,79 +1630,51 @@ extract_handles (const struct GNUNET_NETWORK_FDSet *fdset,
1647 // in fdset must be handled separately 1630 // in fdset must be handled separately
1648 const struct GNUNET_NETWORK_Handle **nhandles; 1631 const struct GNUNET_NETWORK_Handle **nhandles;
1649 const struct GNUNET_DISK_FileHandle **fhandles; 1632 const struct GNUNET_DISK_FileHandle **fhandles;
1650 unsigned int nhandle_count, fhandle_count; 1633 unsigned int nhandles_len, fhandles_len;
1651 int sock; 1634 int sock;
1652 int ret; 1635 int ret;
1653 1636
1654 nhandles = NULL; 1637 nhandles = NULL;
1655 fhandles = NULL; 1638 fhandles = NULL;
1656 nhandle_count = 0; 1639 nhandles_len = 0;
1657 fhandle_count = 0; 1640 fhandles_len = 0;
1658 ret = GNUNET_OK; 1641 ret = GNUNET_OK;
1659 for (sock = 0; sock != fdset->nsds; ++sock) 1642 for (sock = 0; sock != fdset->nsds; ++sock)
1660 { 1643 {
1661 if (GNUNET_YES == GNUNET_NETWORK_fdset_test_native (fdset, sock)) 1644 if (GNUNET_YES == GNUNET_NETWORK_fdset_test_native (fdset, sock))
1662 { 1645 {
1663 const struct GNUNET_NETWORK_Handle *nhandle; 1646 struct GNUNET_NETWORK_Handle *nhandle;
1664 const struct GNUNET_DISK_FileHandle *fhandle; 1647 struct GNUNET_DISK_FileHandle *fhandle;
1665 1648
1666 nhandle = GNUNET_NETWORK_socket_box_native (sock); 1649 nhandle = GNUNET_NETWORK_socket_box_native (sock);
1667 if (NULL != nhandle) 1650 if (NULL != nhandle)
1668 { 1651 {
1669 GNUNET_array_append (nhandles, nhandle_count, nhandle); 1652 GNUNET_array_append (nhandles, nhandles_len, nhandle);
1670 } 1653 }
1671 else 1654 else
1672 { 1655 {
1673 fhandle = GNUNET_DISK_get_handle_from_int_fd (sock); 1656 fhandle = GNUNET_DISK_get_handle_from_int_fd (sock);
1674 if (NULL == fhandle) 1657 if (NULL != fhandle)
1675 { 1658 {
1676 ret = GNUNET_SYSERR; 1659 GNUNET_array_append (fhandles, fhandles_len, fhandle);
1677 // DEBUG
1678 GNUNET_assert (0);
1679 } 1660 }
1680 else 1661 else
1681 { 1662 {
1682 GNUNET_array_append (fhandles, fhandle_count, fhandle); 1663 ret = GNUNET_SYSERR;
1664 // DEBUG
1665 GNUNET_assert (0);
1683 } 1666 }
1684 } 1667 }
1685 } 1668 }
1686 } 1669 }
1687 *ntarget = nhandles; 1670 *ntarget = nhandles_len > 0 ? nhandles : NULL;
1688 *ftarget = fhandles; 1671 *ftarget = fhandles_len > 0 ? fhandles : NULL;
1689 *extracted_nhandles = nhandle_count; 1672 *extracted_nhandles = nhandles_len;
1690 *extracted_fhandles = fhandle_count; 1673 *extracted_fhandles = fhandles_len;
1691 return ret; 1674 return ret;
1692} 1675}
1693 1676
1694 1677
1695void
1696destroy_network_handles (const struct GNUNET_NETWORK_Handle **handles,
1697 unsigned int handles_len)
1698{
1699 size_t i;
1700
1701 for (i = 0; i != handles_len; ++i)
1702 {
1703 GNUNET_free ((void *) handles[i]);
1704 }
1705 GNUNET_array_grow (handles, handles_len, 0);
1706}
1707
1708
1709void
1710destroy_file_handles (const struct GNUNET_DISK_FileHandle **handles,
1711 unsigned int handles_len)
1712{
1713 size_t i;
1714
1715 for (i = 0; i != handles_len; ++i)
1716 {
1717 GNUNET_free ((void *) handles[i]);
1718 }
1719 GNUNET_array_grow (handles, handles_len, 0);
1720}
1721
1722
1723/** 1678/**
1724 * Schedule a new task to be run with a specified delay or when any of 1679 * Schedule a new task to be run with a specified delay or when any of
1725 * the specified file descriptor sets is ready. The delay can be used 1680 * the specified file descriptor sets is ready. The delay can be used
@@ -1757,8 +1712,10 @@ GNUNET_SCHEDULER_add_select (enum GNUNET_SCHEDULER_Priority prio,
1757 void *task_cls) 1712 void *task_cls)
1758{ 1713{
1759 struct GNUNET_SCHEDULER_Task *t; 1714 struct GNUNET_SCHEDULER_Task *t;
1760 const struct GNUNET_NETWORK_Handle **read_nhandles, **write_nhandles; 1715 const struct GNUNET_NETWORK_Handle **read_nhandles;
1761 const struct GNUNET_DISK_FileHandle **read_fhandles, **write_fhandles; 1716 const struct GNUNET_NETWORK_Handle **write_nhandles;
1717 const struct GNUNET_DISK_FileHandle **read_fhandles;
1718 const struct GNUNET_DISK_FileHandle **write_fhandles;
1762 unsigned int read_nhandles_len, write_nhandles_len, 1719 unsigned int read_nhandles_len, write_nhandles_len,
1763 read_fhandles_len, write_fhandles_len; 1720 read_fhandles_len, write_fhandles_len;
1764 1721
@@ -1777,13 +1734,15 @@ GNUNET_SCHEDULER_add_select (enum GNUNET_SCHEDULER_Priority prio,
1777 t->callback_cls = task_cls; 1734 t->callback_cls = task_cls;
1778 t->read_fd = -1; 1735 t->read_fd = -1;
1779 t->write_fd = -1; 1736 t->write_fd = -1;
1737 t->own_handlers = GNUNET_YES;
1780 read_nhandles_len = 0; 1738 read_nhandles_len = 0;
1781 write_nhandles_len = 0; 1739 write_nhandles_len = 0;
1782 read_fhandles_len = 0; 1740 read_fhandles_len = 0;
1783 write_fhandles_len = 0; 1741 write_fhandles_len = 0;
1784 if (NULL != rs) 1742 if (NULL != rs)
1785 { 1743 {
1786 extract_handles (rs, 1744 extract_handles (t,
1745 rs,
1787 &read_nhandles, 1746 &read_nhandles,
1788 &read_nhandles_len, 1747 &read_nhandles_len,
1789 &read_fhandles, 1748 &read_fhandles,
@@ -1791,7 +1750,8 @@ GNUNET_SCHEDULER_add_select (enum GNUNET_SCHEDULER_Priority prio,
1791 } 1750 }
1792 if (NULL != ws) 1751 if (NULL != ws)
1793 { 1752 {
1794 extract_handles (ws, 1753 extract_handles (t,
1754 ws,
1795 &write_nhandles, 1755 &write_nhandles,
1796 &write_nhandles_len, 1756 &write_nhandles_len,
1797 &write_fhandles, 1757 &write_fhandles,
@@ -1807,10 +1767,12 @@ GNUNET_SCHEDULER_add_select (enum GNUNET_SCHEDULER_Priority prio,
1807 read_fhandles_len, 1767 read_fhandles_len,
1808 write_fhandles, 1768 write_fhandles,
1809 write_fhandles_len); 1769 write_fhandles_len);
1810 destroy_network_handles (read_nhandles, read_nhandles_len); 1770 /* free the arrays of pointers to network / file handles, the actual
1811 destroy_network_handles (write_nhandles, write_nhandles_len); 1771 * handles will be freed in destroy_task */
1812 destroy_file_handles (read_fhandles, read_fhandles_len); 1772 GNUNET_array_grow (read_nhandles, read_nhandles_len, 0);
1813 destroy_file_handles (write_fhandles, write_fhandles_len); 1773 GNUNET_array_grow (write_nhandles, write_nhandles_len, 0);
1774 GNUNET_array_grow (read_fhandles, read_fhandles_len, 0);
1775 GNUNET_array_grow (write_fhandles, write_fhandles_len, 0);
1814#if PROFILE_DELAYS 1776#if PROFILE_DELAYS
1815 t->start_time = GNUNET_TIME_absolute_get (); 1777 t->start_time = GNUNET_TIME_absolute_get ();
1816#endif 1778#endif