NULL,
 };
 
-#define GPCI_MAX_DATA_BYTES \
-       (1024 - sizeof(struct hv_get_perf_counter_info_params))
+#define HGPCI_REQ_BUFFER_SIZE  4096
+#define HGPCI_MAX_DATA_BYTES \
+       (HGPCI_REQ_BUFFER_SIZE - sizeof(struct hv_get_perf_counter_info_params))
+
+DEFINE_PER_CPU(char, hv_gpci_reqb[HGPCI_REQ_BUFFER_SIZE]) __aligned(sizeof(uint64_t));
+
+struct hv_gpci_request_buffer {
+       struct hv_get_perf_counter_info_params params;
+       uint8_t bytes[HGPCI_MAX_DATA_BYTES];
+} __packed;
 
 static unsigned long single_gpci_request(u32 req, u32 starting_index,
                u16 secondary_index, u8 version_in, u32 offset, u8 length,
        unsigned long ret;
        size_t i;
        u64 count;
+       struct hv_gpci_request_buffer *arg;
+
+       arg = (void *)get_cpu_var(hv_gpci_reqb);
+       memset(arg, 0, HGPCI_REQ_BUFFER_SIZE);
 
-       struct {
-               struct hv_get_perf_counter_info_params params;
-               uint8_t bytes[GPCI_MAX_DATA_BYTES];
-       } __packed __aligned(sizeof(uint64_t)) arg = {
-               .params = {
-                       .counter_request = cpu_to_be32(req),
-                       .starting_index = cpu_to_be32(starting_index),
-                       .secondary_index = cpu_to_be16(secondary_index),
-                       .counter_info_version_in = version_in,
-               }
-       };
+       arg->params.counter_request = cpu_to_be32(req);
+       arg->params.starting_index = cpu_to_be32(starting_index);
+       arg->params.secondary_index = cpu_to_be16(secondary_index);
+       arg->params.counter_info_version_in = version_in;
 
        ret = plpar_hcall_norets(H_GET_PERF_COUNTER_INFO,
-                       virt_to_phys(&arg), sizeof(arg));
+                       virt_to_phys(arg), HGPCI_REQ_BUFFER_SIZE);
        if (ret) {
                pr_devel("hcall failed: 0x%lx\n", ret);
-               return ret;
+               goto out;
        }
 
        /*
         */
        count = 0;
        for (i = offset; i < offset + length; i++)
-               count |= arg.bytes[i] << (i - offset);
+               count |= arg->bytes[i] << (i - offset);
 
        *value = count;
+out:
+       put_cpu_var(hv_gpci_reqb);
        return ret;
 }
 
        }
 
        /* last byte within the buffer? */
-       if ((event_get_offset(event) + length) > GPCI_MAX_DATA_BYTES) {
+       if ((event_get_offset(event) + length) > HGPCI_MAX_DATA_BYTES) {
                pr_devel("request outside of buffer: %zu > %zu\n",
                                (size_t)event_get_offset(event) + length,
-                               GPCI_MAX_DATA_BYTES);
+                               HGPCI_MAX_DATA_BYTES);
                return -EINVAL;
        }