/** * gssdp_resource_group_remove_resource: * @resource_group: A #GSSDPResourceGroup * @resource_id: The ID of the resource to remove * * Removes the resource with ID @resource_id from @resource_group. **/ void gssdp_resource_group_remove_resource (GSSDPResourceGroup *resource_group, guint resource_id) { GSSDPResourceGroupPrivate *priv; GList *l; g_return_if_fail (GSSDP_IS_RESOURCE_GROUP (resource_group)); g_return_if_fail (resource_id > 0); priv = gssdp_resource_group_get_instance_private (resource_group); for (l = priv->resources; l; l = l->next) { Resource *resource; resource = l->data; if (resource->id == resource_id) { priv->resources = g_list_remove (priv->resources, resource); resource_free (resource); return; } } }
/** * gssdp_resource_group_remove_resource: * @resource_group: An @GSSDPResourceGroup * @resource_id: The ID of the resource to remove * * Removes the resource with ID @resource_id from @resource_group. **/ void gssdp_resource_group_remove_resource (GSSDPResourceGroup *resource_group, guint resource_id) { GList *l; g_return_if_fail (GSSDP_IS_RESOURCE_GROUP (resource_group)); g_return_if_fail (resource_id > 0); for (l = resource_group->priv->resources; l; l = l->next) { Resource *resource; resource = l->data; if (resource->id == resource_id) { resource_group->priv->resources = g_list_remove (resource_group->priv->resources, resource); resource_free (resource); return; } } }
/* * Terminates a process using the SIGINT signal. * * The parameters for this function are pointers to pointers of a struct so that * the underlying pointer can be changed by this function. * * PARAMETERD * pcb: Pointer to the PCB to restart. * * RETURN VALUE * A pointer to the same process, or NULL if terminating the process failed. */ PCB * terminate_PCB(PCB ** pcb) { int status; #ifdef DEBUG fprintf(__DEBUG_OUTPUT, "Terminating PCB %d (PID: %d). Remaining CPU time: %d\n", (*pcb)->id, (int) (*pcb)->pid, (*pcb)->remaining_cpu_time); #endif // #ifdef DEBUG // Send the kill signal if (kill((*pcb)->pid, SIGINT)) { fprintf(__ERROR_OUTPUT, "Termination of PCB %d (PID: %d) failed.\n", (*pcb)->id, (int) (*pcb)->pid); return NULL; } // Wait for the process to respond to the signal waitpid((*pcb)->pid, &status, WUNTRACED); // Free the memory associated with the process #ifdef DEBUG fprintf(__DEBUG_OUTPUT, "Freeing the memory associated with PCB %d.\n", (*pcb)->id); #endif // #ifdef DEBUG (*pcb)->memory = mem_free((*pcb)->memory); // Free the resources associated with the process #ifdef DEBUG fprintf(__DEBUG_OUTPUT, "Freeing the resources associated with PCB %d.\n", (*pcb)->id); #endif // #ifdef DEBUG resource_free(*pcb); return *pcb; }
static void gssdp_resource_group_dispose (GObject *object) { GSSDPResourceGroup *resource_group; GSSDPResourceGroupPrivate *priv; resource_group = GSSDP_RESOURCE_GROUP (object); priv = resource_group->priv; while (priv->resources) { resource_free (priv->resources->data); priv->resources = g_list_delete_link (priv->resources, priv->resources); } if (priv->message_queue) { /* send messages without usual delay */ while (!g_queue_is_empty (priv->message_queue)) { if (priv->available) process_queue (resource_group); else g_free (g_queue_pop_head (priv->message_queue)); } g_queue_free (priv->message_queue); priv->message_queue = NULL; } if (priv->message_src) { g_source_destroy (priv->message_src); priv->message_src = NULL; } if (priv->timeout_src) { g_source_destroy (priv->timeout_src); priv->timeout_src = NULL; } if (priv->client) { if (g_signal_handler_is_connected (priv->client, priv->message_received_id)) { g_signal_handler_disconnect (priv->client, priv->message_received_id); } g_object_unref (priv->client); priv->client = NULL; } G_OBJECT_CLASS (gssdp_resource_group_parent_class)->dispose (object); }
int intr_disconnect(intrec *idesc) { intrec **hook, *head; int irq; int errcode = 0; if (idesc == NULL) return (-1); irq = idesc->intr; /* find pointer that keeps the reference to this interrupt descriptor */ hook = find_pred(idesc, irq); if (hook == NULL) return (-1); /* make copy of original list head, the line after may overwrite it */ head = intreclist_head[irq]; /* unlink: make predecessor point to idesc->next instead of to idesc */ *hook = idesc->next; /* now check whether the element we removed was the list head */ if (idesc == head) { intrmask_t oldspl = splq(1 << irq); /* we want to remove the list head, which was known to intr_mux */ icu_unset(irq, (inthand2_t*)intr_mux); /* check whether the new list head is the only element on list */ head = intreclist_head[irq]; if (head != NULL) { if (head->next != NULL) { /* install the multiplex handler with new list head as argument */ errcode = icu_setup(irq, (inthand2_t*)intr_mux, head, 0, 0); if (errcode == 0) update_intrname(irq, -1); } else { /* install the one remaining handler for this irq */ errcode = icu_setup(irq, head->handler, head->argument, head->maskptr, head->flags); if (errcode == 0) update_intrname(irq, (intptr_t)head->devdata); } } splx(oldspl); } update_masks(idesc->maskptr, irq); #ifdef RESOURCE_CHECK resource_free(idesc->devdata); #endif /* RESOURCE_CHECK */ return (0); }
/** * Constructor for the Eupnp_Service_Info class. * * @param udn service's udn * @param location service's location. For UPnP this is the base URL, for SSDP * this is the service's location. * @param service_type service's type * @param resource Resource from which the other service attributes (e.g. udn, * location) depend on. * @param resource_free Function used to free the resource * * @return On success, a Eupnp_Service_Info instance. Otherwise, NULL. */ EAPI Eupnp_Service_Info * eupnp_service_info_new(const char *udn, const char *location, const char *service_type, void *resource, void (* resource_free)(void *resource)) { /* FIXME Location can point to a root device XML (upnp) or just to the * service's location (ssdp). * * In the first case, this service will be published to the user, who might * request for a proxy. For retrieving this proxy, we need both base_URL and * control_url - the first we already have, but the latter is only defined * inside the root device's XML, so we need to fetch this XML and find this * service's control_url. * TODO 1 or 2 below * 1. Write a simple and fast parser for retrieving this control_url * 2. Adapt eupnp_device_parser.c to implement feature specified on item 1 * * In the second case (SSDP), there's no control URL and we're fine by just * announcing it. * TODO Add a global app option for skipping/disabling UPnP stuff and working * only on SSDP mode. */ CHECK_NULL_RET(udn, NULL); Eupnp_Service_Info *d; d = calloc(1, sizeof(Eupnp_Service_Info)); if (!d) { ERR("Failed to allocate memory for service info"); if (resource && resource_free) resource_free(resource); return NULL; } d->udn = udn; d->location = location; d->service_type = service_type; d->refcount = 1; d->_resource = resource; d->_resource_free = resource_free; DBG("Created new service %p", d); return d; }
static void _tree_destructor(void *data) { propfind_recursive_element_t *element = data; resource_free(element->self); resource_free(element->children); SAFE_FREE(element); }
static void propfind_results_recursive(void *userdata, const ne_uri *uri, const ne_prop_result_set *set) { struct resource *newres = 0; const char *clength, *modtime, *file_id = NULL; const char *resourcetype = NULL; const char *md5sum = NULL; const ne_status *status = NULL; char *path = ne_path_unescape( uri->path ); char *parentPath; char *propfindRootUri = (char*) userdata; propfind_recursive_element_t *element = NULL; propfind_recursive_element_t *pElement = NULL; int depth = 0; (void) status; (void) propfindRootUri; if (!propfind_recursive_cache) { c_rbtree_create(&propfind_recursive_cache, _key_cmp, _data_cmp); } /* Fill the resource structure with the data about the file */ newres = c_malloc(sizeof(struct resource)); ZERO_STRUCTP(newres); newres->uri = path; /* no need to strdup because ne_path_unescape already allocates */ newres->name = c_basename( path ); modtime = ne_propset_value( set, &ls_props[0] ); clength = ne_propset_value( set, &ls_props[1] ); resourcetype = ne_propset_value( set, &ls_props[2] ); md5sum = ne_propset_value( set, &ls_props[3] ); file_id = ne_propset_value( set, &ls_props[4] ); newres->type = resr_normal; if( resourcetype && strncmp( resourcetype, "<DAV:collection>", 16 ) == 0) { newres->type = resr_collection; propfind_recursive_cache_folder_count++; } else { /* DEBUG_WEBDAV("propfind_results_recursive %s [%d]", newres->uri, newres->type); */ propfind_recursive_cache_file_count++; } if (modtime) { newres->modtime = oc_httpdate_parse(modtime); } /* DEBUG_WEBDAV("Parsing Modtime: %s -> %llu", modtime, (unsigned long long) newres->modtime ); */ newres->size = 0; if (clength) { newres->size = atoll(clength); /* DEBUG_WEBDAV("Parsed File size for %s from %s: %lld", newres->name, clength, (long long)newres->size ); */ } if( md5sum ) { newres->md5 = csync_normalize_etag(md5sum); } csync_vio_set_file_id(newres->file_id, file_id); /* DEBUG_WEBDAV("propfind_results_recursive %s [%s] %s", newres->uri, newres->type == resr_collection ? "collection" : "file", newres->md5); */ /* Create new item in rb tree */ if (newres->type == resr_collection) { DEBUG_WEBDAV("propfind_results_recursive %s is a folder", newres->uri); /* Check if in rb tree */ element = c_rbtree_node_data(c_rbtree_find(propfind_recursive_cache,uri->path)); /* If not, create a new item and insert it */ if (!element) { element = c_malloc(sizeof(propfind_recursive_element_t)); element->self = resource_dup(newres); element->children = NULL; element->parent = NULL; c_rbtree_insert(propfind_recursive_cache, element); /* DEBUG_WEBDAV("results_recursive Added collection %s", newres->uri); */ } } /* Check for parent in tree. If exists: Insert it into the children elements there */ parentPath = ne_path_parent(uri->path); if (parentPath) { propfind_recursive_element_t *parentElement = NULL; parentElement = c_rbtree_node_data(c_rbtree_find(propfind_recursive_cache,parentPath)); free(parentPath); if (parentElement) { newres->next = parentElement->children; parentElement->children = newres; /* If the current result is a collection we also need to set its parent */ if (element) element->parent = parentElement; pElement = element; while (pElement) { depth++; pElement = pElement->parent; } if (depth > propfind_recursive_cache_depth) { DEBUG_WEBDAV("propfind_results_recursive %s new maximum tree depth %d", newres->uri, depth); propfind_recursive_cache_depth = depth; } /* DEBUG_WEBDAV("results_recursive Added child %s to collection %s", newres->uri, element->self->uri); */ } else { /* DEBUG_WEBDAV("results_recursive No parent %s found for child %s", parentPath, newres->uri); */ resource_free(newres); newres = NULL; } } }
/** * gssdp_resource_group_add_resource: * @resource_group: An @GSSDPResourceGroup * @target: The resource's target * @usn: The resource's USN * @locations: (element-type utf8): A #GList of the resource's locations * * Adds a resource with target @target, USN @usn, and locations @locations * to @resource_group. * * Return value: The ID of the added resource. **/ guint gssdp_resource_group_add_resource (GSSDPResourceGroup *resource_group, const char *target, const char *usn, GList *locations) { LOGD("gssdp_resource_group_add_resource"); LOGD("gssdp_resource_group_add_resource"); LOGD("gssdp_resource_group_add_resource"); Resource *resource; GList *l; GError *error; g_return_val_if_fail (GSSDP_IS_RESOURCE_GROUP (resource_group), 0); g_return_val_if_fail (target != NULL, 0); g_return_val_if_fail (usn != NULL, 0); g_return_val_if_fail (locations != NULL, 0); resource = g_slice_new0 (Resource); resource->resource_group = resource_group; resource->target = g_strdup (target); resource->usn = g_strdup (usn); error = NULL; resource->target_regex = create_target_regex (target, &resource->version, &error); if (error) { LOGD("Error compiling regular expression for '%s': %s", target, error->message); LOGD("Error compiling regular expression for '%s': %s", target, error->message); LOGD("Error compiling regular expression for '%s': %s", target, error->message); g_warning ("Error compiling regular expression for '%s': %s", target, error->message); g_error_free (error); resource_free (resource); return 0; } resource->initial_byebye_sent = FALSE; for (l = locations; l; l = l->next) { resource->locations = g_list_append (resource->locations, g_strdup (l->data)); } resource_group->priv->resources = g_list_prepend (resource_group->priv->resources, resource); resource->id = ++resource_group->priv->last_resource_id; if (resource_group->priv->available) resource_alive (resource); LOGD("g_list_prepend"); LOGD("g_list_prepend"); LOGD("g_list_prepend"); return resource->id; }
static void propfind_results_recursive_callback(void *userdata, const ne_uri *uri, const ne_prop_result_set *set) { struct resource *newres = 0; const ne_status *status = NULL; char *path = ne_path_unescape( uri->path ); char *parentPath; propfind_recursive_element_t *element = NULL; propfind_recursive_element_t *pElement = NULL; int depth = 0; csync_owncloud_ctx_t *ctx = (csync_owncloud_ctx_t*) userdata; (void) status; if (!ctx->propfind_recursive_cache) { c_rbtree_create(&ctx->propfind_recursive_cache, _key_cmp, _data_cmp); } /* Fill the resource structure with the data about the file */ newres = c_malloc(sizeof(struct resource)); newres->uri = path; /* no need to strdup because ne_path_unescape already allocates */ newres->name = c_basename( path ); fill_webdav_properties_into_resource(newres, set); if( newres->type == resr_collection) { ctx->propfind_recursive_cache_folder_count++; } else { ctx->propfind_recursive_cache_file_count++; } /* Create new item in rb tree */ if (newres->type == resr_collection) { DEBUG_WEBDAV("propfind_results_recursive %s is a folder", newres->uri); /* Check if in rb tree */ element = c_rbtree_node_data(c_rbtree_find(ctx->propfind_recursive_cache,uri->path)); /* If not, create a new item and insert it */ if (!element) { element = c_malloc(sizeof(propfind_recursive_element_t)); element->self = resource_dup(newres); element->self->next = 0; element->children = NULL; element->parent = NULL; c_rbtree_insert(ctx->propfind_recursive_cache, element); /* DEBUG_WEBDAV("results_recursive Added collection %s", newres->uri); */ } } /* Check for parent in tree. If exists: Insert it into the children elements there */ parentPath = ne_path_parent(uri->path); if (parentPath) { propfind_recursive_element_t *parentElement = NULL; parentElement = c_rbtree_node_data(c_rbtree_find(ctx->propfind_recursive_cache,parentPath)); free(parentPath); if (parentElement) { newres->next = parentElement->children; parentElement->children = newres; /* If the current result is a collection we also need to set its parent */ if (element) element->parent = parentElement; pElement = element; while (pElement) { depth++; pElement = pElement->parent; } if (depth > ctx->propfind_recursive_cache_depth) { DEBUG_WEBDAV("propfind_results_recursive %s new maximum tree depth %d", newres->uri, depth); ctx->propfind_recursive_cache_depth = depth; } /* DEBUG_WEBDAV("results_recursive Added child %s to collection %s", newres->uri, element->self->uri); */ return; } } resource_free(newres); newres = NULL; }
/** * gssdp_resource_group_add_resource: * @resource_group: A #GSSDPResourceGroup * @target: The resource's target * @usn: The resource's USN * @locations: (element-type utf8): A #GList of the resource's locations * * Adds a resource with target @target, USN @usn, and locations @locations * to @resource_group. * * Return value: The ID of the added resource. **/ guint gssdp_resource_group_add_resource (GSSDPResourceGroup *resource_group, const char *target, const char *usn, GList *locations) { GSSDPResourceGroupPrivate *priv = NULL; Resource *resource = NULL; GError *error = NULL; g_return_val_if_fail (GSSDP_IS_RESOURCE_GROUP (resource_group), 0); g_return_val_if_fail (target != NULL, 0); g_return_val_if_fail (usn != NULL, 0); g_return_val_if_fail (locations != NULL, 0); priv = gssdp_resource_group_get_instance_private (resource_group); resource = g_slice_new0 (Resource); resource->resource_group = resource_group; resource->target = g_strdup (target); resource->usn = g_strdup (usn); resource->target_regex = create_target_regex (target, &resource->version, &error); if (error) { g_warning ("Error compiling regular expression for '%s': %s", target, error->message); g_error_free (error); resource_free (resource); return 0; } resource->initial_byebye_sent = FALSE; resource->locations = g_list_copy_deep (locations, (GCopyFunc) g_strdup, NULL); priv->resources = g_list_prepend (priv->resources, resource); resource->id = ++priv->last_resource_id; if (priv->available) resource_alive (resource); return resource->id; }