gboolean nmp_netns_pop (NMPNetns *self) { NetnsInfo *info; int ns_types; g_return_val_if_fail (NMP_IS_NETNS (self), FALSE); _stack_ensure_init (); info = _stack_peek (); g_return_val_if_fail (info, FALSE); g_return_val_if_fail (info->netns == self, FALSE); if (info->count > 1) { info->count--; _LOGt (self, "pop#%u* (decrease count to %d)", _stack_size () - 1, info->count); return TRUE; } g_return_val_if_fail (info->count == 1, FALSE); /* cannot pop the original netns. */ g_return_val_if_fail (_stack_size () > 1, FALSE); _LOGD (self, "pop#%u", _stack_size () - 1); ns_types = info->ns_types; _stack_pop (); return _netns_switch_pop (self, ns_types); }
static gboolean _nmp_netns_push_type (NMPNetns *self, int ns_types) { NetnsInfo *info; char sbuf[100]; _stack_ensure_init (); info = _stack_peek (); g_return_val_if_fail (info, FALSE); if (info->netns == self && info->ns_types == ns_types) { info->count++; _LOGt (self, "push#%u* %s (increase count to %d)", _stack_size () - 1, _ns_types_to_str (ns_types, ns_types, sbuf), info->count); return TRUE; } _LOGD (self, "push#%u %s", _stack_size (), _ns_types_to_str (ns_types, _stack_current_ns_types (self, ns_types), sbuf)); if (!_netns_switch_push (self, ns_types)) return FALSE; _stack_push (self, ns_types); return TRUE; }
static void _save_stack(struct coroutine *co) { size_t size = _stack_size(co->sched, co->stack_lowest); assert(size <= co->sched->stack.ss_size); co->stack_base = realloc(co->stack_base, size); co->stack_size = size; memcpy(co->stack_base, _stack_addr(co->sched, size), size); }