ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/Coro/Coro/State.xs
(Generate patch)

Comparing Coro/Coro/State.xs (file contents):
Revision 1.274 by root, Sat Nov 15 00:08:30 2008 UTC vs.
Revision 1.275 by root, Sat Nov 15 06:26:52 2008 UTC

1990 if (PL_op->op_ppaddr != PL_ppaddr [OP_ENTERSUB] 1990 if (PL_op->op_ppaddr != PL_ppaddr [OP_ENTERSUB]
1991 && PL_op->op_ppaddr != pp_slf) 1991 && PL_op->op_ppaddr != pp_slf)
1992 croak ("FATAL: Coro SLF calls can only be made normally, not via goto or any other means, caught"); 1992 croak ("FATAL: Coro SLF calls can only be made normally, not via goto or any other means, caught");
1993 1993
1994 if (items > 3) 1994 if (items > 3)
1995 croak ("Coro only supports up to three arguments to SLF functions currently, caught"); 1995 croak ("Coro only supports up to three arguments to SLF functions currently (not %d), caught", items);
1996 1996
1997 CvFLAGS (cv) |= CVf_SLF; 1997 CvFLAGS (cv) |= CVf_SLF;
1998 CvXSUBANY (cv).any_ptr = (void *)init_cb; 1998 CvXSUBANY (cv).any_ptr = (void *)init_cb;
1999 slf_cv = cv; 1999 slf_cv = cv;
2000 2000
2013 PL_op->op_ppaddr = pp_slf; 2013 PL_op->op_ppaddr = pp_slf;
2014 2014
2015 PL_op = (OP *)&slf_restore; 2015 PL_op = (OP *)&slf_restore;
2016} 2016}
2017 2017
2018/*****************************************************************************/
2019
2020static int
2021slf_check_semaphore_down (pTHX_ struct CoroSLF *frame)
2022{
2023 AV *av = (AV *)frame->data;
2024 SV *count_sv = AvARRAY (av)[0];
2025
2026 if (SvIVX (count_sv) > 0)
2027 {
2028 SvIVX (count_sv) = SvIVX (count_sv) - 1;
2029 return 0;
2030 }
2031 else
2032 {
2033 int i;
2034 /* if we were woken up but can't down, we look through the whole */
2035 /* waiters list and only add us if we aren't in there already */
2036 /* this avoids some degenerate memory usage cases */
2037
2038 for (i = 1; i <= AvFILLp (av); ++i)
2039 if (AvARRAY (av)[i] == SvRV (coro_current))
2040 return 1;
2041
2042 av_push (av, SvREFCNT_inc (SvRV (coro_current)));
2043 return 1;
2044 }
2045}
2046
2047static void
2048slf_init_semaphore_down (pTHX_ struct CoroSLF *frame, SV **arg, int items)
2049{
2050 AV *av = (AV *)SvRV (arg [0]);
2051
2052 if (SvIVX (AvARRAY (av)[0]) > 0)
2053 {
2054 frame->data = (void *)av;
2055 frame->prepare = prepare_nop;
2056 }
2057 else
2058 {
2059 av_push (av, SvREFCNT_inc (SvRV (coro_current)));
2060
2061 frame->data = (void *)sv_2mortal (SvREFCNT_inc ((SV *)av));
2062 frame->prepare = prepare_schedule;
2063 }
2064
2065 frame->check = slf_check_semaphore_down;
2066
2067}
2068
2018MODULE = Coro::State PACKAGE = Coro::State PREFIX = api_ 2069MODULE = Coro::State PACKAGE = Coro::State PREFIX = api_
2019 2070
2020PROTOTYPES: DISABLE 2071PROTOTYPES: DISABLE
2021 2072
2022BOOT: 2073BOOT:
2129 CODE: 2180 CODE:
2130 _exit (code); 2181 _exit (code);
2131 2182
2132int 2183int
2133cctx_stacksize (int new_stacksize = 0) 2184cctx_stacksize (int new_stacksize = 0)
2185 PROTOTYPE: ;$
2134 CODE: 2186 CODE:
2135 RETVAL = cctx_stacksize; 2187 RETVAL = cctx_stacksize;
2136 if (new_stacksize) 2188 if (new_stacksize)
2137 { 2189 {
2138 cctx_stacksize = new_stacksize; 2190 cctx_stacksize = new_stacksize;
2141 OUTPUT: 2193 OUTPUT:
2142 RETVAL 2194 RETVAL
2143 2195
2144int 2196int
2145cctx_max_idle (int max_idle = 0) 2197cctx_max_idle (int max_idle = 0)
2198 PROTOTYPE: ;$
2146 CODE: 2199 CODE:
2147 RETVAL = cctx_max_idle; 2200 RETVAL = cctx_max_idle;
2148 if (max_idle > 1) 2201 if (max_idle > 1)
2149 cctx_max_idle = max_idle; 2202 cctx_max_idle = max_idle;
2150 OUTPUT: 2203 OUTPUT:
2151 RETVAL 2204 RETVAL
2152 2205
2153int 2206int
2154cctx_count () 2207cctx_count ()
2208 PROTOTYPE:
2155 CODE: 2209 CODE:
2156 RETVAL = cctx_count; 2210 RETVAL = cctx_count;
2157 OUTPUT: 2211 OUTPUT:
2158 RETVAL 2212 RETVAL
2159 2213
2160int 2214int
2161cctx_idle () 2215cctx_idle ()
2216 PROTOTYPE:
2162 CODE: 2217 CODE:
2163 RETVAL = cctx_idle; 2218 RETVAL = cctx_idle;
2164 OUTPUT: 2219 OUTPUT:
2165 RETVAL 2220 RETVAL
2166 2221
2167void 2222void
2168list () 2223list ()
2224 PROTOTYPE:
2169 PPCODE: 2225 PPCODE:
2170{ 2226{
2171 struct coro *coro; 2227 struct coro *coro;
2172 for (coro = coro_first; coro; coro = coro->next) 2228 for (coro = coro_first; coro; coro = coro->next)
2173 if (coro->hv) 2229 if (coro->hv)
2240 SvREFCNT_dec (self->throw); 2296 SvREFCNT_dec (self->throw);
2241 self->throw = SvOK (throw) ? newSVsv (throw) : 0; 2297 self->throw = SvOK (throw) ? newSVsv (throw) : 0;
2242 2298
2243void 2299void
2244api_trace (SV *coro, int flags = CC_TRACE | CC_TRACE_SUB) 2300api_trace (SV *coro, int flags = CC_TRACE | CC_TRACE_SUB)
2301 PROTOTYPE: $;$
2245 C_ARGS: aTHX_ coro, flags 2302 C_ARGS: aTHX_ coro, flags
2246 2303
2247SV * 2304SV *
2248has_cctx (Coro::State coro) 2305has_cctx (Coro::State coro)
2249 PROTOTYPE: $ 2306 PROTOTYPE: $
2274 OUTPUT: 2331 OUTPUT:
2275 RETVAL 2332 RETVAL
2276 2333
2277void 2334void
2278force_cctx () 2335force_cctx ()
2336 PROTOTYPE:
2279 CODE: 2337 CODE:
2280 struct coro *coro = SvSTATE (coro_current); 2338 struct coro *coro = SvSTATE (coro_current);
2281 coro->cctx->idle_sp = 0; 2339 coro->cctx->idle_sp = 0;
2282 2340
2283void 2341void
2369 coro_readyhook = SvOK (hook) ? newSVsv (hook) : 0; 2427 coro_readyhook = SvOK (hook) ? newSVsv (hook) : 0;
2370 UNLOCK; 2428 UNLOCK;
2371 2429
2372int 2430int
2373prio (Coro::State coro, int newprio = 0) 2431prio (Coro::State coro, int newprio = 0)
2432 PROTOTYPE: $;$
2374 ALIAS: 2433 ALIAS:
2375 nice = 1 2434 nice = 1
2376 CODE: 2435 CODE:
2377{ 2436{
2378 RETVAL = coro->prio; 2437 RETVAL = coro->prio;
2442 { 2501 {
2443 av_fill (defav, len - 1); 2502 av_fill (defav, len - 1);
2444 for (i = 0; i < len; ++i) 2503 for (i = 0; i < len; ++i)
2445 av_store (defav, i, SvREFCNT_inc_NN (AvARRAY (invoke_av)[i + 1])); 2504 av_store (defav, i, SvREFCNT_inc_NN (AvARRAY (invoke_av)[i + 1]));
2446 } 2505 }
2447
2448 SvREFCNT_dec (invoke);
2449} 2506}
2450 2507
2451void 2508void
2452_pool_2 (SV *cb) 2509_pool_2 (SV *cb)
2453 CODE: 2510 CODE:
2531 2588
2532MODULE = Coro::State PACKAGE = Coro::AIO 2589MODULE = Coro::State PACKAGE = Coro::AIO
2533 2590
2534void 2591void
2535_get_state (SV *self) 2592_get_state (SV *self)
2593 PROTOTYPE: $
2536 PPCODE: 2594 PPCODE:
2537{ 2595{
2538 AV *defav = GvAV (PL_defgv); 2596 AV *defav = GvAV (PL_defgv);
2539 AV *av = newAV (); 2597 AV *av = newAV ();
2540 int i; 2598 int i;
2585BOOT: 2643BOOT:
2586 sv_activity = coro_get_sv (aTHX_ "Coro::AnyEvent::ACTIVITY", TRUE); 2644 sv_activity = coro_get_sv (aTHX_ "Coro::AnyEvent::ACTIVITY", TRUE);
2587 2645
2588SV * 2646SV *
2589_schedule (...) 2647_schedule (...)
2590 PROTOTYPE: @
2591 CODE: 2648 CODE:
2592{ 2649{
2593 static int incede; 2650 static int incede;
2594 2651
2595 api_cede_notself (aTHX); 2652 api_cede_notself (aTHX);
2614MODULE = Coro::State PACKAGE = PerlIO::cede 2671MODULE = Coro::State PACKAGE = PerlIO::cede
2615 2672
2616BOOT: 2673BOOT:
2617 PerlIO_define_layer (aTHX_ &PerlIO_cede); 2674 PerlIO_define_layer (aTHX_ &PerlIO_cede);
2618 2675
2676MODULE = Coro::State PACKAGE = Coro::Semaphore
2677
2678SV *
2679new (SV *klass, SV *count_ = 0)
2680 CODE:
2681{
2682 /* a semaphore contains a counter IV in $sem->[0] and any waiters after that */
2683 AV *av = newAV ();
2684 av_push (av, newSViv (count_ && SvOK (count_) ? SvIV (count_) : 1));
2685 RETVAL = sv_bless (newRV_noinc ((SV *)av), GvSTASH (CvGV (cv)));
2686}
2687 OUTPUT:
2688 RETVAL
2689
2690SV *
2691count (SV *self)
2692 CODE:
2693 RETVAL = newSVsv (AvARRAY ((AV *)SvRV (self))[0]);
2694 OUTPUT:
2695 RETVAL
2696
2697void
2698up (SV *self, int adjust = 1)
2699 ALIAS:
2700 adjust = 1
2701 CODE:
2702{
2703 AV *av = (AV *)SvRV (self);
2704 SV *count_sv = AvARRAY (av)[0];
2705 IV count = SvIVX (count_sv);
2706
2707 count += ix ? adjust : 1;
2708 SvIVX (count_sv) = count;
2709
2710 /* now wake up as many waiters as possible */
2711 while (count > 0 && AvFILLp (av) >= count)
2712 {
2713 SV *cb;
2714
2715 /* swap first two elements so we can shift a waiter */
2716 AvARRAY (av)[0] = AvARRAY (av)[1];
2717 AvARRAY (av)[1] = count_sv;
2718 cb = av_shift (av);
2719
2720 if (SvOBJECT (cb))
2721 api_ready (cb);
2722 else
2723 croak ("callbacks not yet supported");
2724
2725 SvREFCNT_dec (cb);
2726 }
2727}
2728
2729void
2730down (SV *self)
2731 CODE:
2732 api_execute_slf (aTHX_ cv, slf_init_semaphore_down, &ST (0), items);
2733
2734void
2735try (SV *self)
2736 PPCODE:
2737{
2738 AV *av = (AV *)SvRV (self);
2739 SV *count_sv = AvARRAY (av)[0];
2740 IV count = SvIVX (count_sv);
2741
2742 if (count > 0)
2743 {
2744 --count;
2745 SvIVX (count_sv) = count;
2746 XSRETURN_YES;
2747 }
2748 else
2749 XSRETURN_NO;
2750}
2751
2752void
2753waiters (SV *self)
2754 CODE:
2755{
2756 AV *av = (AV *)SvRV (self);
2757
2758 if (GIMME_V == G_SCALAR)
2759 XPUSHs (sv_2mortal (newSVsv (AvARRAY (av)[0])));
2760 else
2761 {
2762 int i;
2763 EXTEND (SP, AvFILLp (av) + 1 - 1);
2764 for (i = 1; i <= AvFILLp (av); ++i)
2765 PUSHs (newSVsv (AvARRAY (av)[i]));
2766 }
2767}
2768

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines