Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

PCI/ACPI: move _OSC code to pci_root.c

Move PCI _OSC management code from drivers/pci/pci-acpi.c to
drivers/acpi/pci_root.c. The benefits are

- We no longer need struct osc_data and its management code (contents
are moved to struct acpi_pci_root). This simplify the code, and we
no longer care about kmalloc() failure.

- We can make pci_acpi_osc_support() be a static function, which is
called only from drivers/acpi/pci_root.c.

Signed-off-by: Kenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
Reviewed-by: Andrew Patterson <andrew.patterson@hp.com>
Tested-by: Andrew Patterson <andrew.patterson@hp.com>
Acked-by: Alex Chiang <achiang@hp.com>
Signed-off-by: Jesse Barnes <jbarnes@virtuousgeek.org>

authored by

Kenji Kaneshige and committed by
Jesse Barnes
63f10f0f 5fe5db05

+178 -218
+178 -2
drivers/acpi/pci_root.c
··· 66 66 struct acpi_device * device; 67 67 struct acpi_pci_id id; 68 68 struct pci_bus *bus; 69 + 70 + u32 osc_support_set; /* _OSC state of support bits */ 71 + u32 osc_control_set; /* _OSC state of control bits */ 72 + u32 osc_control_qry; /* the latest _OSC query result */ 73 + 74 + u32 osc_queried:1; /* has _OSC control been queried? */ 69 75 }; 70 76 71 77 static LIST_HEAD(acpi_pci_roots); 72 78 73 79 static struct acpi_pci_driver *sub_driver; 80 + static DEFINE_MUTEX(osc_lock); 74 81 75 82 int acpi_pci_register_driver(struct acpi_pci_driver *driver) 76 83 { ··· 192 185 } 193 186 } 194 187 188 + static u8 OSC_UUID[16] = {0x5B, 0x4D, 0xDB, 0x33, 0xF7, 0x1F, 0x1C, 0x40, 189 + 0x96, 0x57, 0x74, 0x41, 0xC0, 0x3D, 0xD7, 0x66}; 190 + 191 + static acpi_status acpi_pci_run_osc(acpi_handle handle, 192 + const u32 *capbuf, u32 *retval) 193 + { 194 + acpi_status status; 195 + struct acpi_object_list input; 196 + union acpi_object in_params[4]; 197 + struct acpi_buffer output = {ACPI_ALLOCATE_BUFFER, NULL}; 198 + union acpi_object *out_obj; 199 + u32 errors; 200 + 201 + /* Setting up input parameters */ 202 + input.count = 4; 203 + input.pointer = in_params; 204 + in_params[0].type = ACPI_TYPE_BUFFER; 205 + in_params[0].buffer.length = 16; 206 + in_params[0].buffer.pointer = OSC_UUID; 207 + in_params[1].type = ACPI_TYPE_INTEGER; 208 + in_params[1].integer.value = 1; 209 + in_params[2].type = ACPI_TYPE_INTEGER; 210 + in_params[2].integer.value = 3; 211 + in_params[3].type = ACPI_TYPE_BUFFER; 212 + in_params[3].buffer.length = 12; 213 + in_params[3].buffer.pointer = (u8 *)capbuf; 214 + 215 + status = acpi_evaluate_object(handle, "_OSC", &input, &output); 216 + if (ACPI_FAILURE(status)) 217 + return status; 218 + 219 + if (!output.length) 220 + return AE_NULL_OBJECT; 221 + 222 + out_obj = output.pointer; 223 + if (out_obj->type != ACPI_TYPE_BUFFER) { 224 + printk(KERN_DEBUG "_OSC evaluation returned wrong type\n"); 225 + status = AE_TYPE; 226 + goto out_kfree; 227 + } 228 + /* Need to ignore the bit0 in result code */ 229 + errors = *((u32 *)out_obj->buffer.pointer) & ~(1 << 0); 230 + if (errors) { 231 + if (errors & OSC_REQUEST_ERROR) 232 + printk(KERN_DEBUG "_OSC request failed\n"); 233 + if (errors & OSC_INVALID_UUID_ERROR) 234 + printk(KERN_DEBUG "_OSC invalid UUID\n"); 235 + if (errors & OSC_INVALID_REVISION_ERROR) 236 + printk(KERN_DEBUG "_OSC invalid revision\n"); 237 + if (errors & OSC_CAPABILITIES_MASK_ERROR) { 238 + if (capbuf[OSC_QUERY_TYPE] & OSC_QUERY_ENABLE) 239 + goto out_success; 240 + printk(KERN_DEBUG 241 + "Firmware did not grant requested _OSC control\n"); 242 + status = AE_SUPPORT; 243 + goto out_kfree; 244 + } 245 + status = AE_ERROR; 246 + goto out_kfree; 247 + } 248 + out_success: 249 + *retval = *((u32 *)(out_obj->buffer.pointer + 8)); 250 + status = AE_OK; 251 + 252 + out_kfree: 253 + kfree(output.pointer); 254 + return status; 255 + } 256 + 257 + static acpi_status acpi_pci_query_osc(struct acpi_pci_root *root, u32 flags) 258 + { 259 + acpi_status status; 260 + u32 support_set, result, capbuf[3]; 261 + 262 + /* do _OSC query for all possible controls */ 263 + support_set = root->osc_support_set | (flags & OSC_SUPPORT_MASKS); 264 + capbuf[OSC_QUERY_TYPE] = OSC_QUERY_ENABLE; 265 + capbuf[OSC_SUPPORT_TYPE] = support_set; 266 + capbuf[OSC_CONTROL_TYPE] = OSC_CONTROL_MASKS; 267 + 268 + status = acpi_pci_run_osc(root->device->handle, capbuf, &result); 269 + if (ACPI_SUCCESS(status)) { 270 + root->osc_support_set = support_set; 271 + root->osc_control_qry = result; 272 + root->osc_queried = 1; 273 + } 274 + return status; 275 + } 276 + 277 + static acpi_status acpi_pci_osc_support(struct acpi_pci_root *root, u32 flags) 278 + { 279 + acpi_status status; 280 + acpi_handle tmp; 281 + 282 + status = acpi_get_handle(root->device->handle, "_OSC", &tmp); 283 + if (ACPI_FAILURE(status)) 284 + return status; 285 + mutex_lock(&osc_lock); 286 + status = acpi_pci_query_osc(root, flags); 287 + mutex_unlock(&osc_lock); 288 + return status; 289 + } 290 + 291 + static struct acpi_pci_root *acpi_pci_find_root(acpi_handle handle) 292 + { 293 + struct acpi_pci_root *root; 294 + list_for_each_entry(root, &acpi_pci_roots, node) { 295 + if (root->device->handle == handle) 296 + return root; 297 + } 298 + return NULL; 299 + } 300 + 301 + /** 302 + * pci_osc_control_set - commit requested control to Firmware 303 + * @handle: acpi_handle for the target ACPI object 304 + * @flags: driver's requested control bits 305 + * 306 + * Attempt to take control from Firmware on requested control bits. 307 + **/ 308 + acpi_status pci_osc_control_set(acpi_handle handle, u32 flags) 309 + { 310 + acpi_status status; 311 + u32 control_req, result, capbuf[3]; 312 + acpi_handle tmp; 313 + struct acpi_pci_root *root; 314 + 315 + status = acpi_get_handle(handle, "_OSC", &tmp); 316 + if (ACPI_FAILURE(status)) 317 + return status; 318 + 319 + control_req = (flags & OSC_CONTROL_MASKS); 320 + if (!control_req) 321 + return AE_TYPE; 322 + 323 + root = acpi_pci_find_root(handle); 324 + if (!root) 325 + return AE_NOT_EXIST; 326 + 327 + mutex_lock(&osc_lock); 328 + /* No need to evaluate _OSC if the control was already granted. */ 329 + if ((root->osc_control_set & control_req) == control_req) 330 + goto out; 331 + 332 + /* Need to query controls first before requesting them */ 333 + if (!root->osc_queried) { 334 + status = acpi_pci_query_osc(root, root->osc_support_set); 335 + if (ACPI_FAILURE(status)) 336 + goto out; 337 + } 338 + if ((root->osc_control_qry & control_req) != control_req) { 339 + printk(KERN_DEBUG 340 + "Firmware did not grant requested _OSC control\n"); 341 + status = AE_SUPPORT; 342 + goto out; 343 + } 344 + 345 + capbuf[OSC_QUERY_TYPE] = 0; 346 + capbuf[OSC_SUPPORT_TYPE] = root->osc_support_set; 347 + capbuf[OSC_CONTROL_TYPE] = root->osc_control_set | control_req; 348 + status = acpi_pci_run_osc(handle, capbuf, &result); 349 + if (ACPI_SUCCESS(status)) 350 + root->osc_control_set = result; 351 + out: 352 + mutex_unlock(&osc_lock); 353 + return status; 354 + } 355 + EXPORT_SYMBOL(pci_osc_control_set); 356 + 195 357 static int __devinit acpi_pci_root_add(struct acpi_device *device) 196 358 { 197 359 int result = 0; ··· 393 217 * PCI domains, so we indicate this in _OSC support capabilities. 394 218 */ 395 219 flags = base_flags = OSC_PCI_SEGMENT_GROUPS_SUPPORT; 396 - pci_acpi_osc_support(device->handle, flags); 220 + acpi_pci_osc_support(root, flags); 397 221 398 222 /* 399 223 * Segment ··· 529 353 if (pci_msi_enabled()) 530 354 flags |= OSC_MSI_SUPPORT; 531 355 if (flags != base_flags) 532 - pci_acpi_osc_support(device->handle, flags); 356 + acpi_pci_osc_support(root, flags); 533 357 534 358 end: 535 359 if (result) {
-215
drivers/pci/pci-acpi.c
··· 18 18 #include <linux/pci-acpi.h> 19 19 #include "pci.h" 20 20 21 - struct acpi_osc_data { 22 - acpi_handle handle; 23 - u32 support_set; 24 - u32 control_set; 25 - u32 control_query; 26 - int is_queried; 27 - struct list_head sibiling; 28 - }; 29 - static LIST_HEAD(acpi_osc_data_list); 30 - 31 - struct acpi_osc_args { 32 - u32 capbuf[3]; 33 - }; 34 - 35 - static DEFINE_MUTEX(pci_acpi_lock); 36 - 37 - static struct acpi_osc_data *acpi_get_osc_data(acpi_handle handle) 38 - { 39 - struct acpi_osc_data *data; 40 - 41 - list_for_each_entry(data, &acpi_osc_data_list, sibiling) { 42 - if (data->handle == handle) 43 - return data; 44 - } 45 - data = kzalloc(sizeof(*data), GFP_KERNEL); 46 - if (!data) 47 - return NULL; 48 - INIT_LIST_HEAD(&data->sibiling); 49 - data->handle = handle; 50 - list_add_tail(&data->sibiling, &acpi_osc_data_list); 51 - return data; 52 - } 53 - 54 - static u8 OSC_UUID[16] = {0x5B, 0x4D, 0xDB, 0x33, 0xF7, 0x1F, 0x1C, 0x40, 55 - 0x96, 0x57, 0x74, 0x41, 0xC0, 0x3D, 0xD7, 0x66}; 56 - 57 - static acpi_status acpi_run_osc(acpi_handle handle, 58 - struct acpi_osc_args *osc_args, u32 *retval) 59 - { 60 - acpi_status status; 61 - struct acpi_object_list input; 62 - union acpi_object in_params[4]; 63 - struct acpi_buffer output = {ACPI_ALLOCATE_BUFFER, NULL}; 64 - union acpi_object *out_obj; 65 - u32 errors, flags = osc_args->capbuf[OSC_QUERY_TYPE]; 66 - 67 - /* Setting up input parameters */ 68 - input.count = 4; 69 - input.pointer = in_params; 70 - in_params[0].type = ACPI_TYPE_BUFFER; 71 - in_params[0].buffer.length = 16; 72 - in_params[0].buffer.pointer = OSC_UUID; 73 - in_params[1].type = ACPI_TYPE_INTEGER; 74 - in_params[1].integer.value = 1; 75 - in_params[2].type = ACPI_TYPE_INTEGER; 76 - in_params[2].integer.value = 3; 77 - in_params[3].type = ACPI_TYPE_BUFFER; 78 - in_params[3].buffer.length = 12; 79 - in_params[3].buffer.pointer = (u8 *)osc_args->capbuf; 80 - 81 - status = acpi_evaluate_object(handle, "_OSC", &input, &output); 82 - if (ACPI_FAILURE(status)) 83 - return status; 84 - 85 - if (!output.length) 86 - return AE_NULL_OBJECT; 87 - 88 - out_obj = output.pointer; 89 - if (out_obj->type != ACPI_TYPE_BUFFER) { 90 - printk(KERN_DEBUG "Evaluate _OSC returns wrong type\n"); 91 - status = AE_TYPE; 92 - goto out_kfree; 93 - } 94 - /* Need to ignore the bit0 in result code */ 95 - errors = *((u32 *)out_obj->buffer.pointer) & ~(1 << 0); 96 - if (errors) { 97 - if (errors & OSC_REQUEST_ERROR) 98 - printk(KERN_DEBUG "_OSC request fails\n"); 99 - if (errors & OSC_INVALID_UUID_ERROR) 100 - printk(KERN_DEBUG "_OSC invalid UUID\n"); 101 - if (errors & OSC_INVALID_REVISION_ERROR) 102 - printk(KERN_DEBUG "_OSC invalid revision\n"); 103 - if (errors & OSC_CAPABILITIES_MASK_ERROR) { 104 - if (flags & OSC_QUERY_ENABLE) 105 - goto out_success; 106 - printk(KERN_DEBUG "_OSC FW not grant req. control\n"); 107 - status = AE_SUPPORT; 108 - goto out_kfree; 109 - } 110 - status = AE_ERROR; 111 - goto out_kfree; 112 - } 113 - out_success: 114 - *retval = *((u32 *)(out_obj->buffer.pointer + 8)); 115 - status = AE_OK; 116 - 117 - out_kfree: 118 - kfree(output.pointer); 119 - return status; 120 - } 121 - 122 - static acpi_status __acpi_query_osc(u32 flags, struct acpi_osc_data *osc_data) 123 - { 124 - acpi_status status; 125 - u32 support_set, result; 126 - struct acpi_osc_args osc_args; 127 - 128 - /* do _OSC query for all possible controls */ 129 - support_set = osc_data->support_set | (flags & OSC_SUPPORT_MASKS); 130 - osc_args.capbuf[OSC_QUERY_TYPE] = OSC_QUERY_ENABLE; 131 - osc_args.capbuf[OSC_SUPPORT_TYPE] = support_set; 132 - osc_args.capbuf[OSC_CONTROL_TYPE] = OSC_CONTROL_MASKS; 133 - 134 - status = acpi_run_osc(osc_data->handle, &osc_args, &result); 135 - if (ACPI_SUCCESS(status)) { 136 - osc_data->support_set = support_set; 137 - osc_data->control_query = result; 138 - osc_data->is_queried = 1; 139 - } 140 - 141 - return status; 142 - } 143 - 144 - /* 145 - * pci_acpi_osc_support: Invoke _OSC indicating support for the given feature 146 - * @flags: Bitmask of flags to support 147 - * 148 - * See the ACPI spec for the definition of the flags 149 - */ 150 - int pci_acpi_osc_support(acpi_handle handle, u32 flags) 151 - { 152 - acpi_status status; 153 - acpi_handle tmp; 154 - struct acpi_osc_data *osc_data; 155 - int rc = 0; 156 - 157 - status = acpi_get_handle(handle, "_OSC", &tmp); 158 - if (ACPI_FAILURE(status)) 159 - return -ENOTTY; 160 - 161 - mutex_lock(&pci_acpi_lock); 162 - osc_data = acpi_get_osc_data(handle); 163 - if (!osc_data) { 164 - printk(KERN_ERR "acpi osc data array is full\n"); 165 - rc = -ENOMEM; 166 - goto out; 167 - } 168 - 169 - __acpi_query_osc(flags, osc_data); 170 - out: 171 - mutex_unlock(&pci_acpi_lock); 172 - return rc; 173 - } 174 - 175 - /** 176 - * pci_osc_control_set - commit requested control to Firmware 177 - * @handle: acpi_handle for the target ACPI object 178 - * @flags: driver's requested control bits 179 - * 180 - * Attempt to take control from Firmware on requested control bits. 181 - **/ 182 - acpi_status pci_osc_control_set(acpi_handle handle, u32 flags) 183 - { 184 - acpi_status status; 185 - u32 control_req, control_set, result; 186 - acpi_handle tmp; 187 - struct acpi_osc_data *osc_data; 188 - struct acpi_osc_args osc_args; 189 - 190 - status = acpi_get_handle(handle, "_OSC", &tmp); 191 - if (ACPI_FAILURE(status)) 192 - return status; 193 - 194 - mutex_lock(&pci_acpi_lock); 195 - osc_data = acpi_get_osc_data(handle); 196 - if (!osc_data) { 197 - printk(KERN_ERR "acpi osc data array is full\n"); 198 - status = AE_ERROR; 199 - goto out; 200 - } 201 - 202 - control_req = (flags & OSC_CONTROL_MASKS); 203 - if (!control_req) { 204 - status = AE_TYPE; 205 - goto out; 206 - } 207 - 208 - /* No need to evaluate _OSC if the control was already granted. */ 209 - if ((osc_data->control_set & control_req) == control_req) 210 - goto out; 211 - 212 - if (!osc_data->is_queried) { 213 - status = __acpi_query_osc(osc_data->support_set, osc_data); 214 - if (ACPI_FAILURE(status)) 215 - goto out; 216 - } 217 - 218 - if ((osc_data->control_query & control_req) != control_req) { 219 - status = AE_SUPPORT; 220 - goto out; 221 - } 222 - 223 - control_set = osc_data->control_set | control_req; 224 - osc_args.capbuf[OSC_QUERY_TYPE] = 0; 225 - osc_args.capbuf[OSC_SUPPORT_TYPE] = osc_data->support_set; 226 - osc_args.capbuf[OSC_CONTROL_TYPE] = control_set; 227 - status = acpi_run_osc(handle, &osc_args, &result); 228 - if (ACPI_SUCCESS(status)) 229 - osc_data->control_set = result; 230 - out: 231 - mutex_unlock(&pci_acpi_lock); 232 - return status; 233 - } 234 - EXPORT_SYMBOL(pci_osc_control_set); 235 - 236 21 /* 237 22 * _SxD returns the D-state with the highest power 238 23 * (lowest D-state number) supported in the S-state "x".
-1
include/linux/pci-acpi.h
··· 50 50 51 51 #ifdef CONFIG_ACPI 52 52 extern acpi_status pci_osc_control_set(acpi_handle handle, u32 flags); 53 - int pci_acpi_osc_support(acpi_handle handle, u32 flags); 54 53 static inline acpi_handle acpi_find_root_bridge_handle(struct pci_dev *pdev) 55 54 { 56 55 /* Find root host bridge */