@@ -58,6 +58,40 @@ struct cdevsw hax_vcpu_cdevsw = {
5858    .d_flag  =  D_OTHER  | D_MPSAFE 
5959};
6060
61+ #define  load_user_data (dest , src , body_len , body_max , arg_t , body_t )          \
62+         void *uaddr = (void *)(*(arg_t **)(src));                             \
63+         size_t size;                                                          \
64+         arg_t header;                                                         \
65+         (dest) = NULL;                                                        \
66+         if (copyin(uaddr, &header, sizeof(arg_t))) {                          \
67+             hax_log(HAX_LOGE, "%s: argument header read error.\n", __func__); \
68+             ret = -EFAULT;                                                    \
69+             break;                                                            \
70+         }                                                                     \
71+         if (header.body_len > (body_max)) {                                   \
72+             hax_log(HAX_LOGW, "%s: %d exceeds argument body maximum %d.\n",   \
73+                     __func__, header.body_len, (body_max));                   \
74+             ret = -E2BIG;                                                     \
75+             break;                                                            \
76+         }                                                                     \
77+         size = sizeof(arg_t) + header.body_len * sizeof(body_t);               \
78+         (dest) = hax_vmalloc(size, HAX_MEM_NONPAGE);                          \
79+         if ((dest) == NULL) {                                                 \
80+             hax_log(HAX_LOGE, "%s: failed to allocate memory.\n", __func__);  \
81+             ret = -ENOMEM;                                                    \
82+             break;                                                            \
83+         }                                                                     \
84+         if (copyin(uaddr, (dest), size)) {                                    \
85+             hax_log(HAX_LOGE, "%s: argument read error.\n", __func__);        \
86+             unload_user_data(dest);                                           \
87+             ret = -EFAULT;                                                    \
88+             break;                                                            \
89+         }
90+ 
91+ #define  unload_user_data (dest )       \
92+         if ((dest) != NULL)          \
93+             hax_vfree((dest), size);
94+ 
6195/* VCPU operations */ 
6296
6397int  hax_vcpu_open (dev_t  self , int  flag  __unused , int  mode  __unused ,
@@ -243,6 +277,14 @@ int hax_vcpu_ioctl(dev_t self, u_long cmd, void *data, int flag,
243277        vcpu_debug (cvcpu , hax_debug );
244278        break ;
245279    }
280+     case  HAX_VCPU_IOCTL_SET_CPUID : {
281+         struct  hax_cpuid  * cpuid ;
282+         load_user_data (cpuid , data , total , HAX_MAX_CPUID_ENTRIES , hax_cpuid ,
283+                        hax_cpuid_entry );
284+         ret  =  vcpu_set_cpuid (cvcpu , cpuid );
285+         unload_user_data (cpuid );
286+         break ;
287+     }
246288    default :
247289        // TODO: Print information about the process that sent the ioctl. 
248290        hax_log (HAX_LOGE , "Unknown VCPU IOCTL %#lx, pid=%d ('%s')\n" , cmd ,
0 commit comments