aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/acpi/executer/exfield.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/acpi/executer/exfield.c')
-rw-r--r--drivers/acpi/executer/exfield.c63
1 files changed, 9 insertions, 54 deletions
diff --git a/drivers/acpi/executer/exfield.c b/drivers/acpi/executer/exfield.c
index 2d88a3d8d1ad..3e440d84226a 100644
--- a/drivers/acpi/executer/exfield.c
+++ b/drivers/acpi/executer/exfield.c
@@ -5,7 +5,7 @@
5 *****************************************************************************/ 5 *****************************************************************************/
6 6
7/* 7/*
8 * Copyright (C) 2000 - 2007, R. Byron Moore 8 * Copyright (C) 2000 - 2008, Intel Corp.
9 * All rights reserved. 9 * All rights reserved.
10 * 10 *
11 * Redistribution and use in source and binary forms, with or without 11 * Redistribution and use in source and binary forms, with or without
@@ -71,7 +71,6 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
71 union acpi_operand_object *buffer_desc; 71 union acpi_operand_object *buffer_desc;
72 acpi_size length; 72 acpi_size length;
73 void *buffer; 73 void *buffer;
74 u8 locked;
75 74
76 ACPI_FUNCTION_TRACE_PTR(ex_read_data_from_field, obj_desc); 75 ACPI_FUNCTION_TRACE_PTR(ex_read_data_from_field, obj_desc);
77 76
@@ -111,9 +110,7 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
111 110
112 /* Lock entire transaction if requested */ 111 /* Lock entire transaction if requested */
113 112
114 locked = 113 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
115 acpi_ex_acquire_global_lock(obj_desc->common_field.
116 field_flags);
117 114
118 /* 115 /*
119 * Perform the read. 116 * Perform the read.
@@ -125,7 +122,7 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
125 buffer.pointer), 122 buffer.pointer),
126 ACPI_READ | (obj_desc->field. 123 ACPI_READ | (obj_desc->field.
127 attribute << 16)); 124 attribute << 16));
128 acpi_ex_release_global_lock(locked); 125 acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
129 goto exit; 126 goto exit;
130 } 127 }
131 128
@@ -175,13 +172,12 @@ acpi_ex_read_data_from_field(struct acpi_walk_state *walk_state,
175 172
176 /* Lock entire transaction if requested */ 173 /* Lock entire transaction if requested */
177 174
178 locked = 175 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
179 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
180 176
181 /* Read from the field */ 177 /* Read from the field */
182 178
183 status = acpi_ex_extract_from_field(obj_desc, buffer, (u32) length); 179 status = acpi_ex_extract_from_field(obj_desc, buffer, (u32) length);
184 acpi_ex_release_global_lock(locked); 180 acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
185 181
186 exit: 182 exit:
187 if (ACPI_FAILURE(status)) { 183 if (ACPI_FAILURE(status)) {
@@ -214,10 +210,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
214{ 210{
215 acpi_status status; 211 acpi_status status;
216 u32 length; 212 u32 length;
217 u32 required_length;
218 void *buffer; 213 void *buffer;
219 void *new_buffer;
220 u8 locked;
221 union acpi_operand_object *buffer_desc; 214 union acpi_operand_object *buffer_desc;
222 215
223 ACPI_FUNCTION_TRACE_PTR(ex_write_data_to_field, obj_desc); 216 ACPI_FUNCTION_TRACE_PTR(ex_write_data_to_field, obj_desc);
@@ -278,9 +271,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
278 271
279 /* Lock entire transaction if requested */ 272 /* Lock entire transaction if requested */
280 273
281 locked = 274 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
282 acpi_ex_acquire_global_lock(obj_desc->common_field.
283 field_flags);
284 275
285 /* 276 /*
286 * Perform the write (returns status and perhaps data in the 277 * Perform the write (returns status and perhaps data in the
@@ -291,7 +282,7 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
291 (acpi_integer *) buffer, 282 (acpi_integer *) buffer,
292 ACPI_WRITE | (obj_desc->field. 283 ACPI_WRITE | (obj_desc->field.
293 attribute << 16)); 284 attribute << 16));
294 acpi_ex_release_global_lock(locked); 285 acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
295 286
296 *result_desc = buffer_desc; 287 *result_desc = buffer_desc;
297 return_ACPI_STATUS(status); 288 return_ACPI_STATUS(status);
@@ -319,35 +310,6 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
319 return_ACPI_STATUS(AE_AML_OPERAND_TYPE); 310 return_ACPI_STATUS(AE_AML_OPERAND_TYPE);
320 } 311 }
321 312
322 /*
323 * We must have a buffer that is at least as long as the field
324 * we are writing to. This is because individual fields are
325 * indivisible and partial writes are not supported -- as per
326 * the ACPI specification.
327 */
328 new_buffer = NULL;
329 required_length =
330 ACPI_ROUND_BITS_UP_TO_BYTES(obj_desc->common_field.bit_length);
331
332 if (length < required_length) {
333
334 /* We need to create a new buffer */
335
336 new_buffer = ACPI_ALLOCATE_ZEROED(required_length);
337 if (!new_buffer) {
338 return_ACPI_STATUS(AE_NO_MEMORY);
339 }
340
341 /*
342 * Copy the original data to the new buffer, starting
343 * at Byte zero. All unused (upper) bytes of the
344 * buffer will be 0.
345 */
346 ACPI_MEMCPY((char *)new_buffer, (char *)buffer, length);
347 buffer = new_buffer;
348 length = required_length;
349 }
350
351 ACPI_DEBUG_PRINT((ACPI_DB_BFIELD, 313 ACPI_DEBUG_PRINT((ACPI_DB_BFIELD,
352 "FieldWrite [FROM]: Obj %p (%s:%X), Buf %p, ByteLen %X\n", 314 "FieldWrite [FROM]: Obj %p (%s:%X), Buf %p, ByteLen %X\n",
353 source_desc, 315 source_desc,
@@ -366,19 +328,12 @@ acpi_ex_write_data_to_field(union acpi_operand_object *source_desc,
366 328
367 /* Lock entire transaction if requested */ 329 /* Lock entire transaction if requested */
368 330
369 locked = 331 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
370 acpi_ex_acquire_global_lock(obj_desc->common_field.field_flags);
371 332
372 /* Write to the field */ 333 /* Write to the field */
373 334
374 status = acpi_ex_insert_into_field(obj_desc, buffer, length); 335 status = acpi_ex_insert_into_field(obj_desc, buffer, length);
375 acpi_ex_release_global_lock(locked); 336 acpi_ex_release_global_lock(obj_desc->common_field.field_flags);
376
377 /* Free temporary buffer if we used one */
378
379 if (new_buffer) {
380 ACPI_FREE(new_buffer);
381 }
382 337
383 return_ACPI_STATUS(status); 338 return_ACPI_STATUS(status);
384} 339}