Advertisement
DirtyJerz

spp_verifier_direct

Nov 7th, 2011
1,162
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 15.89 KB | None | 0 0
  1. dosent work atm
  2. dumps every other
  3. feel free to modify
  4. /*
  5.  * SPP verifier direct
  6.  *
  7.  * This program is free software; you can redistribute it and/or modify it
  8.  * under the terms of the GNU General Public License as published
  9.  * by the Free Software Foundation; version 2 of the License.
  10.  *
  11.  * This program is distributed in the hope that it will be useful, but
  12.  * WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  14.  * General Public License for more details.
  15.  *
  16.  * You should have received a copy of the GNU General Public License along
  17.  * with this program; if not, write to the Free Software Foundation, Inc.,
  18.  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
  19.  */
  20.  
  21. #include <linux/module.h>
  22. #include <linux/kernel.h>
  23. #include <linux/init.h>
  24. #include <linux/proc_fs.h>
  25. #include <linux/workqueue.h>
  26. #include <linux/mmzone.h>
  27. #include <linux/io.h>
  28. #include <linux/mm.h>
  29. #include <linux/file.h>
  30. #include <linux/fs.h>
  31. #include <linux/fcntl.h>
  32. #include <linux/syscalls.h>
  33.  
  34. #include <asm/uaccess.h>
  35. #include <asm/lv1call.h>
  36.  
  37. #include "spu.h"
  38.  
  39. #define PROC_ROOT       "spp_verifier_direct"
  40. #define PROC_METLDR     "metldr"
  41. #define PROC_ISOLDR     "isoldr"
  42. #define PROC_RVKPRG     "rvkprg"
  43. #define PROC_EID0       "eid0"
  44. #define PROC_SPU        "spu"
  45. #define PROC_DEBUG      "debug"
  46. #define PROC_RUN        "run"
  47. #define PROC_PROFILE        "profile"
  48.  
  49. #define METLDR_PAGE_ORDER   4
  50. #define ISOLDR_PAGE_ORDER   5
  51. #define RVKPRG_PAGE_ORDER   0
  52. #define EID0_PAGE_ORDER     0
  53. #define SPU_PAGE_ORDER      5
  54. #define PROFILE_PAGE_ORDER  2
  55. #define LS_ARGS_PAGE_ORDER  0
  56.  
  57. #define DEBUG_SIZE      4096
  58.  
  59. #define EID0_LS_ADDR        0x3e400
  60. #define LDR_ARGS_LS_ADDR    0x3e800
  61. #define RVK_PRG_LS_ADDR     0x3f000
  62.  
  63. /*
  64.  * DPRINTF
  65.  */
  66. #define DPRINTF(fmt, ...)                       \
  67. do {                                    \
  68.     if (debug_size >= (DEBUG_SIZE / 2))             \
  69.         debug_size = 0;                     \
  70.                                     \
  71.     debug_size += sprintf(debug + debug_size, fmt, ## __VA_ARGS__); \
  72. } while (0)
  73.  
  74. struct ldr_args {
  75.     u64 prog_auth_id;
  76.     u64 lpar_auth_id;
  77.     void *spu_module;
  78.     void *spu_module_arg1;
  79.     u64 spu_module_arg1_size;
  80.     void *spu_module_arg2;
  81.     u64 spu_module_arg2_size;
  82.     u8 res1[16];
  83.     u64 field48;
  84.     u8 res2[16];
  85. };
  86.  
  87. static struct proc_dir_entry *proc_root;
  88. static struct proc_dir_entry *proc_metldr;
  89. static struct proc_dir_entry *proc_isoldr;
  90. static struct proc_dir_entry *proc_rvkprg;
  91. static struct proc_dir_entry *proc_eid0;
  92. static struct proc_dir_entry *proc_spu;
  93. static struct proc_dir_entry *proc_debug;
  94. static struct proc_dir_entry *proc_run;
  95. static struct proc_dir_entry *proc_profile;
  96.  
  97. static unsigned char *metldr;
  98. static unsigned char *isoldr;
  99. static unsigned char *rvkprg;
  100. static unsigned char *eid0;
  101. static unsigned char *spu;
  102.  
  103. static unsigned char *debug;
  104. static unsigned long debug_size;
  105.  
  106. static unsigned char *profile;
  107.  
  108. static unsigned char *ls_args;
  109.  
  110. static struct workqueue_struct *workqueue;
  111. static struct work_struct work;
  112.  
  113. static int force_exit;
  114.  
  115. /*
  116.  * proc_generic_open
  117.  */
  118. static int proc_generic_open(struct inode *inode, struct file *file)
  119. {
  120.     struct proc_dir_entry *proc = PDE(inode);
  121.  
  122.     file->private_data = proc;
  123.  
  124.     return 0;
  125. }
  126.  
  127. /*
  128.  * proc_generic_release
  129.  */
  130. static int proc_generic_release(struct inode *inode, struct file *file)
  131. {
  132.     return 0;
  133. }
  134.  
  135. /*
  136.  * proc_generic_read
  137.  */
  138. static ssize_t proc_generic_read(struct file *file, char __user *buffer, size_t len, loff_t *off)
  139. {
  140.     struct proc_dir_entry *proc = file->private_data;
  141.     int pos;
  142.  
  143.     pos = *off;
  144.  
  145.     if ((pos >= proc->size) || !len)
  146.         return 0;
  147.  
  148.     if ((pos + len) > proc->size)
  149.         len = proc->size - pos;
  150.  
  151.     if (copy_to_user(buffer, (unsigned char *) proc->data + pos, len))
  152.         return -EFAULT;
  153.  
  154.     *off += len;
  155.  
  156.     return len;
  157. }
  158.  
  159. /*
  160.  * proc_generic_write
  161.  */
  162. static ssize_t proc_generic_write(struct file *file, const char __user *buffer, size_t len, loff_t *off)
  163. {
  164.     struct proc_dir_entry *proc = file->private_data;
  165.     int pos;
  166.  
  167.     pos = *off;
  168.  
  169.     if ((pos >= proc->size) || !len)
  170.         return 0;
  171.  
  172.     if ((pos + len) > proc->size)
  173.         len = proc->size - pos;
  174.  
  175.     if (copy_from_user((unsigned char *) proc->data + pos, buffer, len))
  176.         return -EFAULT;
  177.  
  178.     *off += len;
  179.  
  180.     return len;
  181. }
  182.  
  183. /*
  184.  * work_function
  185.  */
  186. static void work_function(struct work_struct *work)
  187. {
  188.     u64 ppe_id, vas_id;
  189.     u64 priv2_addr, problem_phys, local_store_phys, unused, shadow_addr, spe_id;
  190.     struct spu_shadow *shadow = NULL;
  191.     struct spu_problem *problem = NULL;
  192.     struct spu_priv2 *priv2 = NULL;
  193.     u64 esid, vsid;
  194.     u64 intr_status;
  195.     u32 out_mbox, size;
  196.     int res;
  197.  
  198.     memset(debug, 0, DEBUG_SIZE);
  199.  
  200.     debug_size = 0;
  201.  
  202.     lv1_get_logical_ppe_id(&ppe_id);
  203.     lv1_get_virtual_address_space_id_of_ppe(ppe_id, &vas_id);
  204.  
  205.     DPRINTF("PPE id (0x%016llx) VAS id (0x%016llx)\n", ppe_id, vas_id);
  206.  
  207.     res = lv1_construct_logical_spe(PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT, PAGE_SHIFT,
  208.         vas_id, 0 /* type */, &priv2_addr, &problem_phys, &local_store_phys,
  209.         &unused, &shadow_addr, &spe_id);
  210.  
  211.     DPRINTF("lv1_construct_logical_spe (0x%08x)\n", res);
  212.  
  213.     if (res)
  214.         return;
  215.  
  216.     DPRINTF("SPE id (0x%016llx)\n", spe_id);
  217.  
  218.     res = lv1_enable_logical_spe(spe_id, 6);
  219.  
  220.     DPRINTF("lv1_enable_logical_spe (0x%08x)\n", res);
  221.  
  222.     if (res)
  223.         goto bad;
  224.  
  225.     res = lv1_set_spe_interrupt_mask(spe_id, 0, 0x7);
  226.  
  227.     DPRINTF("lv1_set_spe_interrupt_mask(0) (0x%08x)\n", res);
  228.  
  229.     if (res)
  230.         goto bad;
  231.  
  232.     res = lv1_set_spe_interrupt_mask(spe_id, 1, 0xf);
  233.  
  234.     DPRINTF("lv1_set_spe_interrupt_mask(1) (0x%08x)\n", res);
  235.  
  236.     if (res)
  237.         goto bad;
  238.  
  239.     res = lv1_set_spe_interrupt_mask(spe_id, 2, 0xf);
  240.  
  241.     DPRINTF("lv1_set_spe_interrupt_mask(2) (0x%08x)\n", res);
  242.  
  243.     if (res)
  244.         goto bad;
  245.  
  246.     res = lv1_set_spe_privilege_state_area_1_register(spe_id, MFC_SR1, 0x10);
  247.  
  248.     DPRINTF("lv1_set_spe_privilege_state_area_1_register (0x%08x)\n", res);
  249.  
  250.     if (res)
  251.         goto bad;
  252.  
  253.     shadow = __ioremap(shadow_addr, sizeof(*shadow), _PAGE_NO_CACHE | 3);
  254.     if (!shadow)
  255.         goto bad;
  256.  
  257.     problem = ioremap(problem_phys, sizeof(*problem));
  258.     if (!problem)
  259.         goto bad;
  260.  
  261.     priv2 = ioremap(priv2_addr, sizeof(*priv2));
  262.     if (!priv2)
  263.         goto bad;
  264.  
  265.     esid = (GET_ESID((unsigned long) metldr) << SID_SHIFT) | SLB_ESID_V;
  266.     vsid = (get_kernel_vsid((unsigned long) metldr, MMU_SEGSIZE_256M) << SLB_VSID_SHIFT) |
  267.         SLB_VSID_KP | SLB_VSID_L;
  268.  
  269.     DPRINTF("ea (0x%016llx) esid (0x%016llx) vsid (0x%016llx)\n", (unsigned long long) metldr, esid, vsid);
  270.  
  271.     spu_slb_invalidate_all(priv2);
  272.  
  273.     spu_slb_set_entry(priv2, 0, esid, vsid);
  274.  
  275.     priv2->spu_cfg = 0;
  276.  
  277.     eieio();
  278.  
  279.     spu_in_mbox_write_64(problem, (u64) isoldr);
  280.  
  281.     spu_sig_notify_1_2_write_64(problem, (u64) metldr);
  282.  
  283.     spu_iso_load_req_enable(priv2);
  284.  
  285.     spu_iso_load_req(problem);
  286.  
  287.     while (1) {
  288.         if (force_exit) {
  289.             DPRINTF("exiting\n");
  290.             goto bad;
  291.         }
  292.  
  293.         res = lv1_get_spe_interrupt_status(spe_id, 0, &intr_status);
  294.  
  295.         DPRINTF("lv1_get_spe_interrupt_status(0) (0x%08x)\n", res);
  296.  
  297.         if (res)
  298.             goto bad;
  299.  
  300.         if (intr_status) {
  301.             res = lv1_clear_spe_interrupt_status(spe_id, 0, intr_status, 0);
  302.  
  303.             DPRINTF("lv1_clear_spe_interrupt_status(0) (0x%08x)\n", res);
  304.  
  305.             if (res)
  306.                 goto bad;
  307.         }
  308.  
  309.         res = lv1_get_spe_interrupt_status(spe_id, 1, &intr_status);
  310.  
  311.         DPRINTF("lv1_get_spe_interrupt_status(1) (0x%08x)\n", res);
  312.  
  313.         if (res)
  314.             goto bad;
  315.  
  316.         if (intr_status) {
  317.             res = lv1_clear_spe_interrupt_status(spe_id, 1, intr_status, 0);
  318.  
  319.             DPRINTF("lv1_clear_spe_interrupt_status(1) (0x%08x)\n", res);
  320.  
  321.             if (res)
  322.                 goto bad;
  323.         }
  324.  
  325.         res = lv1_get_spe_interrupt_status(spe_id, 2, &intr_status);
  326.  
  327.         DPRINTF("lv1_get_spe_interrupt_status(2) (0x%08x)\n", res);
  328.  
  329.         if (res)
  330.             goto bad;
  331.  
  332.         if (intr_status & 0x1) {
  333.             /* mailbox interrupt */
  334.  
  335.                         struct file *f = filp_open("/ls.bin", O_RDWR | O_CREAT | O_APPEND | O_SYNC, 0);
  336.  
  337.                         mm_segment_t oldfs;
  338.                         oldfs = get_fs();
  339.                         set_fs (KERNEL_DS);
  340.  
  341.             size = 0;
  342.             while(size <= 0x40000)
  343.             {
  344.                 eieio();
  345.  
  346.                 //Wait for mbox value to be written.
  347.                 while(spu_mbox_stat_intr_out_mbox_count(problem) == 0);
  348.  
  349.                 out_mbox = problem->spu_out_mbox;
  350.  
  351.                 //eieio(); shit.
  352.  
  353.                 f->f_op->write(f,(char *) &problem->spu_out_mbox, sizeof(problem->spu_out_mbox), &f->f_pos);
  354.  
  355.                 DPRINTF("\rdumped 0x%08x of 0x40000", size);
  356.  
  357.                 size += 4;
  358.  
  359.             }
  360.  
  361.                         set_fs(oldfs);
  362.  
  363.                         filp_close(f,NULL);
  364.  
  365.                         fput(f);
  366.  
  367.             goto bad;
  368.  
  369.         res = lv1_clear_spe_interrupt_status(spe_id, 2, intr_status, 0);
  370.  
  371.         DPRINTF("lv1_clear_spe_interrupt_status(2) (0x%08x)\n", res);
  372.  
  373.         if (res)
  374.             goto bad;
  375.         }
  376.  
  377.         if (!(problem->spu_status & 0x1))
  378.             break;
  379.  
  380.         DPRINTF("sleep\n");
  381.  
  382.         set_current_state(TASK_INTERRUPTIBLE);
  383.         schedule_timeout(100);
  384.     }
  385.  
  386.     DPRINTF("problem status (0x%08x)\n", problem->spu_status);
  387.  
  388. bad:
  389.  
  390.     if (shadow)
  391.         iounmap(shadow);
  392.  
  393.     if (problem) {
  394.         spu_stop_req(problem);
  395.         iounmap(problem);
  396.     }
  397.  
  398.     if (priv2)
  399.         iounmap(priv2);
  400.  
  401.     res = lv1_destruct_logical_spe(spe_id);
  402.  
  403.     DPRINTF("lv1_destruct_logical_spe (0x%08x)\n", res);
  404.  
  405. }
  406.  
  407. /*
  408.  * proc_run_write
  409.  */
  410. static int proc_run_write(struct file *file, const char *page, unsigned long count, void *data)
  411. {
  412.     queue_work(workqueue, &work);
  413.  
  414.     return count;
  415. }
  416.  
  417. static struct file_operations proc_generic_fops = {
  418.     .owner   = THIS_MODULE,
  419.     .open    = proc_generic_open,
  420.     .release = proc_generic_release,
  421.     .read    = proc_generic_read,
  422.     .write   = proc_generic_write,
  423. };
  424.  
  425. /*
  426.  * construct_proc
  427.  */
  428. static int construct_proc(void)
  429. {
  430.     proc_root = proc_mkdir(PROC_ROOT, NULL);
  431.     if (!proc_root)
  432.         return -ENOMEM;
  433.  
  434.     proc_metldr = create_proc_entry(PROC_METLDR, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  435.     if (!proc_metldr)
  436.         return -ENOMEM;
  437.  
  438.     proc_metldr->proc_fops = &proc_generic_fops;
  439.     proc_metldr->mode = S_IFREG | S_IRUGO | S_IWUSR;
  440.     proc_metldr->uid = 0;
  441.     proc_metldr->gid = 0;
  442.     proc_metldr->size = (1 << METLDR_PAGE_ORDER) << PAGE_SHIFT;
  443.     proc_metldr->data = metldr;
  444.  
  445.     proc_isoldr = create_proc_entry(PROC_ISOLDR, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  446.     if (!proc_isoldr)
  447.         return -ENOMEM;
  448.  
  449.     proc_isoldr->proc_fops = &proc_generic_fops;
  450.     proc_isoldr->mode = S_IFREG | S_IRUGO | S_IWUSR;
  451.     proc_isoldr->uid = 0;
  452.     proc_isoldr->gid = 0;
  453.     proc_isoldr->size = (1 << ISOLDR_PAGE_ORDER) << PAGE_SHIFT;
  454.     proc_isoldr->data = isoldr;
  455.  
  456.     proc_rvkprg = create_proc_entry(PROC_RVKPRG, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  457.     if (!proc_rvkprg)
  458.         return -ENOMEM;
  459.  
  460.     proc_rvkprg->proc_fops = &proc_generic_fops;
  461.     proc_rvkprg->mode = S_IFREG | S_IRUGO | S_IWUSR;
  462.     proc_rvkprg->uid = 0;
  463.     proc_rvkprg->gid = 0;
  464.     proc_rvkprg->size = (1 << RVKPRG_PAGE_ORDER) << PAGE_SHIFT;
  465.     proc_rvkprg->data = rvkprg;
  466.  
  467.     proc_eid0 = create_proc_entry(PROC_EID0, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  468.     if (!proc_eid0)
  469.         return -ENOMEM;
  470.  
  471.     proc_eid0->proc_fops = &proc_generic_fops;
  472.     proc_eid0->mode = S_IFREG | S_IRUGO | S_IWUSR;
  473.     proc_eid0->uid = 0;
  474.     proc_eid0->gid = 0;
  475.     proc_eid0->size = (1 << EID0_PAGE_ORDER) << PAGE_SHIFT;
  476.     proc_eid0->data = eid0;
  477.  
  478.     proc_spu = create_proc_entry(PROC_SPU, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  479.     if (!proc_spu)
  480.         return -ENOMEM;
  481.  
  482.     proc_spu->proc_fops = &proc_generic_fops;
  483.     proc_spu->mode = S_IFREG | S_IRUGO | S_IWUSR;
  484.     proc_spu->uid = 0;
  485.     proc_spu->gid = 0;
  486.     proc_spu->size = (1 << SPU_PAGE_ORDER) << PAGE_SHIFT;
  487.     proc_spu->data = spu;
  488.  
  489.     proc_debug = create_proc_entry(PROC_DEBUG, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  490.     if (!proc_debug)
  491.         return -ENOMEM;
  492.  
  493.     proc_debug->proc_fops = &proc_generic_fops;
  494.     proc_debug->mode = S_IFREG | S_IRUGO | S_IWUSR;
  495.     proc_debug->uid = 0;
  496.     proc_debug->gid = 0;
  497.     proc_debug->size = DEBUG_SIZE;
  498.     proc_debug->data = debug;
  499.  
  500.     proc_run = create_proc_entry(PROC_RUN, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  501.     if (!proc_run)
  502.         return -ENOMEM;
  503.  
  504.     proc_run->write_proc = proc_run_write;
  505.  
  506.     proc_profile = create_proc_entry(PROC_PROFILE, S_IFREG | S_IRUGO | S_IWUSR, proc_root);
  507.     if (!proc_profile)
  508.         return -ENOMEM;
  509.  
  510.     proc_profile->proc_fops = &proc_generic_fops;
  511.     proc_profile->mode = S_IFREG | S_IRUGO | S_IWUSR;
  512.     proc_profile->uid = 0;
  513.     proc_profile->gid = 0;
  514.     proc_profile->size = (1 << PROFILE_PAGE_ORDER) << PAGE_SHIFT;
  515.     proc_profile->data = profile;
  516.  
  517.     return 0;
  518. }
  519.  
  520. /*
  521.  * destruct_proc
  522.  */
  523. static void destruct_proc(void)
  524. {
  525.     if (proc_profile)
  526.         remove_proc_entry(PROC_PROFILE, proc_root);
  527.  
  528.     if (proc_run)
  529.         remove_proc_entry(PROC_RUN, proc_root);
  530.  
  531.     if (proc_debug)
  532.         remove_proc_entry(PROC_DEBUG, proc_root);
  533.  
  534.     if (proc_spu)
  535.         remove_proc_entry(PROC_SPU, proc_root);
  536.  
  537.     if (proc_eid0)
  538.         remove_proc_entry(PROC_EID0, proc_root);
  539.  
  540.     if (proc_rvkprg)
  541.         remove_proc_entry(PROC_RVKPRG, proc_root);
  542.  
  543.     if (proc_isoldr)
  544.         remove_proc_entry(PROC_ISOLDR, proc_root);
  545.  
  546.     if (proc_metldr)
  547.         remove_proc_entry(PROC_METLDR, proc_root);
  548.  
  549.     remove_proc_entry(PROC_ROOT, NULL);
  550. }
  551.  
  552. /*
  553.  * spp_verifier_direct_init
  554.  */
  555. static int __init spp_verifier_direct_init(void)
  556. {
  557.     int res;
  558.  
  559.     metldr = (unsigned char *) __get_free_pages(GFP_KERNEL, METLDR_PAGE_ORDER);
  560.     if (!metldr) {
  561.         res = -ENOMEM;
  562.         goto bad1;
  563.     }
  564.  
  565.     memset(metldr, 0, (1 << METLDR_PAGE_ORDER) << PAGE_SHIFT);
  566.  
  567.     isoldr = (unsigned char *) __get_free_pages(GFP_KERNEL, ISOLDR_PAGE_ORDER);
  568.     if (!isoldr) {
  569.         res = -ENOMEM;
  570.         goto bad2;
  571.     }
  572.  
  573.     memset(isoldr, 0, (1 << ISOLDR_PAGE_ORDER) << PAGE_SHIFT);
  574.  
  575.     rvkprg = (unsigned char *) __get_free_pages(GFP_KERNEL, RVKPRG_PAGE_ORDER);
  576.     if (!rvkprg) {
  577.         res = -ENOMEM;
  578.         goto bad3;
  579.     }
  580.  
  581.     memset(rvkprg, 0, (1 << RVKPRG_PAGE_ORDER) << PAGE_SHIFT);
  582.  
  583.     eid0 = (unsigned char *) __get_free_pages(GFP_KERNEL, EID0_PAGE_ORDER);
  584.     if (!eid0) {
  585.         res = -ENOMEM;
  586.         goto bad4;
  587.     }
  588.  
  589.     memset(eid0, 0, (1 << EID0_PAGE_ORDER) << PAGE_SHIFT);
  590.  
  591.     spu = (unsigned char *) __get_free_pages(GFP_KERNEL, SPU_PAGE_ORDER);
  592.     if (!spu) {
  593.         res = -ENOMEM;
  594.         goto bad5;
  595.     }
  596.  
  597.     memset(spu, 0, (1 << SPU_PAGE_ORDER) << PAGE_SHIFT);
  598.  
  599.     debug = kzalloc(DEBUG_SIZE, GFP_KERNEL);
  600.     if (!debug) {
  601.         res = -ENOMEM;
  602.         goto bad6;
  603.     }
  604.  
  605.     profile = (unsigned char *) __get_free_pages(GFP_KERNEL, PROFILE_PAGE_ORDER);
  606.     if (!profile) {
  607.         res = -ENOMEM;
  608.         goto bad7;
  609.     }
  610.  
  611.     memset(profile, 0, (1 << PROFILE_PAGE_ORDER) << PAGE_SHIFT);
  612.  
  613.     ls_args = (unsigned char *) __get_free_pages(GFP_KERNEL, LS_ARGS_PAGE_ORDER);
  614.     if (!ls_args) {
  615.         res = -ENOMEM;
  616.         goto bad8;
  617.     }
  618.  
  619.     memset(ls_args, 0, (1 << LS_ARGS_PAGE_ORDER) << PAGE_SHIFT);
  620.  
  621.     res = construct_proc();
  622.     if (res)
  623.         goto bad9;
  624.  
  625.     INIT_WORK(&work, work_function);
  626.  
  627.     workqueue = create_singlethread_workqueue("spp_verifier_direct_wq");
  628.     if (!workqueue) {
  629.         res = -ENOMEM;
  630.         goto bad9;
  631.     }
  632.  
  633.     return 0;
  634.  
  635. bad9:
  636.  
  637.     destruct_proc();
  638.     free_pages((unsigned long) ls_args, LS_ARGS_PAGE_ORDER);
  639.  
  640. bad8:
  641.  
  642.     free_pages((unsigned long) profile, PROFILE_PAGE_ORDER);
  643.  
  644. bad7:
  645.  
  646.     kfree(debug);
  647.  
  648. bad6:
  649.  
  650.     free_pages((unsigned long) spu, SPU_PAGE_ORDER);
  651.  
  652. bad5:
  653.  
  654.     free_pages((unsigned long) eid0, EID0_PAGE_ORDER);
  655.  
  656. bad4:
  657.  
  658.     free_pages((unsigned long) rvkprg, RVKPRG_PAGE_ORDER);
  659.  
  660. bad3:
  661.  
  662.     free_pages((unsigned long) isoldr, ISOLDR_PAGE_ORDER);
  663.  
  664. bad2:
  665.  
  666.     free_pages((unsigned long) metldr, METLDR_PAGE_ORDER);
  667.  
  668. bad1:
  669.  
  670.     return res;
  671. }
  672.  
  673. /*
  674.  * spp_verifier_direct_exit
  675.  */
  676. static void __exit spp_verifier_direct_exit(void)
  677. {
  678.     force_exit = 1;
  679.  
  680.     destroy_workqueue(workqueue);
  681.  
  682.     destruct_proc();
  683.  
  684.     if (metldr)
  685.         free_pages((unsigned long) metldr, METLDR_PAGE_ORDER);
  686.  
  687.     if (isoldr)
  688.         free_pages((unsigned long) isoldr, ISOLDR_PAGE_ORDER);
  689.  
  690.     if (rvkprg)
  691.         free_pages((unsigned long) rvkprg, RVKPRG_PAGE_ORDER);
  692.  
  693.     if (eid0)
  694.         free_pages((unsigned long) eid0, EID0_PAGE_ORDER);
  695.  
  696.     if (spu)
  697.         free_pages((unsigned long) spu, SPU_PAGE_ORDER);
  698.  
  699.     if (debug)
  700.         kfree(debug);
  701.  
  702.     if (profile)
  703.         free_pages((unsigned long) profile, PROFILE_PAGE_ORDER);
  704.  
  705.     if (ls_args)
  706.         free_pages((unsigned long) ls_args, LS_ARGS_PAGE_ORDER);
  707. }
  708.  
  709. module_init(spp_verifier_direct_init);
  710. module_exit(spp_verifier_direct_exit);
  711.  
  712. MODULE_LICENSE("GPL");
  713. MODULE_DESCRIPTION("SPP verifier direct");
  714. MODULE_AUTHOR("glevand");
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement