void lwt_fini () { int i; lwt_control(0, 0); for (i = 0; i < cfs_num_online_cpus(); i++) while (lwt_cpus[i].lwtc_current_page != NULL) { lwt_page_t *lwtp = lwt_cpus[i].lwtc_current_page; if (cfs_list_empty (&lwtp->lwtp_list)) { lwt_cpus[i].lwtc_current_page = NULL; } else { lwt_cpus[i].lwtc_current_page = cfs_list_entry (lwtp->lwtp_list.next, lwt_page_t, lwtp_list); cfs_list_del (&lwtp->lwtp_list); } __free_page (lwtp->lwtp_page); LIBCFS_FREE (lwtp, sizeof (*lwtp)); } }
static int libcfs_ioctl_int(struct cfs_psdev_file *pfile,unsigned long cmd, void *arg, struct libcfs_ioctl_data *data) { int err = -EINVAL; ENTRY; switch (cmd) { case IOC_LIBCFS_CLEAR_DEBUG: libcfs_debug_clear_buffer(); RETURN(0); /* * case IOC_LIBCFS_PANIC: * Handled in arch/cfs_module.c */ case IOC_LIBCFS_MARK_DEBUG: if (data->ioc_inlbuf1 == NULL || data->ioc_inlbuf1[data->ioc_inllen1 - 1] != '\0') RETURN(-EINVAL); libcfs_debug_mark_buffer(data->ioc_inlbuf1); RETURN(0); #if LWT_SUPPORT case IOC_LIBCFS_LWT_CONTROL: err = lwt_control ((data->ioc_flags & 1) != 0, (data->ioc_flags & 2) != 0); break; case IOC_LIBCFS_LWT_SNAPSHOT: { cfs_cycles_t now; int ncpu; int total_size; err = lwt_snapshot (&now, &ncpu, &total_size, data->ioc_pbuf1, data->ioc_plen1); data->ioc_u64[0] = now; data->ioc_u32[0] = ncpu; data->ioc_u32[1] = total_size; /* Hedge against broken user/kernel typedefs (e.g. cycles_t) */ data->ioc_u32[2] = sizeof(lwt_event_t); data->ioc_u32[3] = offsetof(lwt_event_t, lwte_where); if (err == 0 && libcfs_ioctl_popdata(arg, data, sizeof (*data))) err = -EFAULT; break; } case IOC_LIBCFS_LWT_LOOKUP_STRING: err = lwt_lookup_string (&data->ioc_count, data->ioc_pbuf1, data->ioc_pbuf2, data->ioc_plen2); if (err == 0 && libcfs_ioctl_popdata(arg, data, sizeof (*data))) err = -EFAULT; break; #endif case IOC_LIBCFS_MEMHOG: if (pfile->private_data == NULL) { err = -EINVAL; } else { kportal_memhog_free(pfile->private_data); /* XXX The ioc_flags is not GFP flags now, need to be fixed */ err = kportal_memhog_alloc(pfile->private_data, data->ioc_count, data->ioc_flags); if (err != 0) kportal_memhog_free(pfile->private_data); } break; case IOC_LIBCFS_PING_TEST: { extern void (kping_client)(struct libcfs_ioctl_data *); void (*ping)(struct libcfs_ioctl_data *); CDEBUG(D_IOCTL, "doing %d pings to nid %s (%s)\n", data->ioc_count, libcfs_nid2str(data->ioc_nid), libcfs_nid2str(data->ioc_nid)); ping = symbol_get(kping_client); if (!ping) { CERROR("symbol_get failed\n"); } else { ping(data); symbol_put(kping_client); } RETURN(0); } default: { struct libcfs_ioctl_handler *hand; err = -EINVAL; down_read(&ioctl_list_sem); cfs_list_for_each_entry_typed(hand, &ioctl_list, struct libcfs_ioctl_handler, item) { err = hand->handle_ioctl(cmd, data); if (err != -EINVAL) { if (err == 0) err = libcfs_ioctl_popdata(arg, data, sizeof (*data)); break; } } up_read(&ioctl_list_sem); break; } } RETURN(err); }