diff options
Diffstat (limited to 'drivers/acpi/acpica/hwgpe.c')
-rw-r--r-- | drivers/acpi/acpica/hwgpe.c | 94 |
1 files changed, 65 insertions, 29 deletions
diff --git a/drivers/acpi/acpica/hwgpe.c b/drivers/acpi/acpica/hwgpe.c index bd72319a38f0..3450309c2786 100644 --- a/drivers/acpi/acpica/hwgpe.c +++ b/drivers/acpi/acpica/hwgpe.c | |||
@@ -57,21 +57,47 @@ acpi_hw_enable_wakeup_gpe_block(struct acpi_gpe_xrupt_info *gpe_xrupt_info, | |||
57 | 57 | ||
58 | /****************************************************************************** | 58 | /****************************************************************************** |
59 | * | 59 | * |
60 | * FUNCTION: acpi_hw_low_disable_gpe | 60 | * FUNCTION: acpi_hw_gpe_register_bit |
61 | * | ||
62 | * PARAMETERS: gpe_event_info - Info block for the GPE | ||
63 | * gpe_register_info - Info block for the GPE register | ||
64 | * | ||
65 | * RETURN: Status | ||
66 | * | ||
67 | * DESCRIPTION: Compute GPE enable mask with one bit corresponding to the given | ||
68 | * GPE set. | ||
69 | * | ||
70 | ******************************************************************************/ | ||
71 | |||
72 | u32 acpi_hw_gpe_register_bit(struct acpi_gpe_event_info *gpe_event_info, | ||
73 | struct acpi_gpe_register_info *gpe_register_info) | ||
74 | { | ||
75 | return (u32)1 << (gpe_event_info->gpe_number - | ||
76 | gpe_register_info->base_gpe_number); | ||
77 | } | ||
78 | |||
79 | /****************************************************************************** | ||
80 | * | ||
81 | * FUNCTION: acpi_hw_low_set_gpe | ||
61 | * | 82 | * |
62 | * PARAMETERS: gpe_event_info - Info block for the GPE to be disabled | 83 | * PARAMETERS: gpe_event_info - Info block for the GPE to be disabled |
84 | * action - Enable or disable | ||
63 | * | 85 | * |
64 | * RETURN: Status | 86 | * RETURN: Status |
65 | * | 87 | * |
66 | * DESCRIPTION: Disable a single GPE in the enable register. | 88 | * DESCRIPTION: Enable or disable a single GPE in its enable register. |
67 | * | 89 | * |
68 | ******************************************************************************/ | 90 | ******************************************************************************/ |
69 | 91 | ||
70 | acpi_status acpi_hw_low_disable_gpe(struct acpi_gpe_event_info *gpe_event_info) | 92 | acpi_status |
93 | acpi_hw_low_set_gpe(struct acpi_gpe_event_info *gpe_event_info, u8 action) | ||
71 | { | 94 | { |
72 | struct acpi_gpe_register_info *gpe_register_info; | 95 | struct acpi_gpe_register_info *gpe_register_info; |
73 | acpi_status status; | 96 | acpi_status status; |
74 | u32 enable_mask; | 97 | u32 enable_mask; |
98 | u32 register_bit; | ||
99 | |||
100 | ACPI_FUNCTION_ENTRY(); | ||
75 | 101 | ||
76 | /* Get the info block for the entire GPE register */ | 102 | /* Get the info block for the entire GPE register */ |
77 | 103 | ||
@@ -87,11 +113,27 @@ acpi_status acpi_hw_low_disable_gpe(struct acpi_gpe_event_info *gpe_event_info) | |||
87 | return (status); | 113 | return (status); |
88 | } | 114 | } |
89 | 115 | ||
90 | /* Clear just the bit that corresponds to this GPE */ | 116 | /* Set ot clear just the bit that corresponds to this GPE */ |
91 | 117 | ||
92 | ACPI_CLEAR_BIT(enable_mask, ((u32)1 << | 118 | register_bit = acpi_hw_gpe_register_bit(gpe_event_info, |
93 | (gpe_event_info->gpe_number - | 119 | gpe_register_info); |
94 | gpe_register_info->base_gpe_number))); | 120 | switch (action) { |
121 | case ACPI_GPE_COND_ENABLE: | ||
122 | if (!(register_bit & gpe_register_info->enable_for_run)) | ||
123 | return (AE_BAD_PARAMETER); | ||
124 | |||
125 | case ACPI_GPE_ENABLE: | ||
126 | ACPI_SET_BIT(enable_mask, register_bit); | ||
127 | break; | ||
128 | |||
129 | case ACPI_GPE_DISABLE: | ||
130 | ACPI_CLEAR_BIT(enable_mask, register_bit); | ||
131 | break; | ||
132 | |||
133 | default: | ||
134 | ACPI_ERROR((AE_INFO, "Invalid action\n")); | ||
135 | return (AE_BAD_PARAMETER); | ||
136 | } | ||
95 | 137 | ||
96 | /* Write the updated enable mask */ | 138 | /* Write the updated enable mask */ |
97 | 139 | ||
@@ -116,23 +158,11 @@ acpi_status acpi_hw_low_disable_gpe(struct acpi_gpe_event_info *gpe_event_info) | |||
116 | acpi_status | 158 | acpi_status |
117 | acpi_hw_write_gpe_enable_reg(struct acpi_gpe_event_info * gpe_event_info) | 159 | acpi_hw_write_gpe_enable_reg(struct acpi_gpe_event_info * gpe_event_info) |
118 | { | 160 | { |
119 | struct acpi_gpe_register_info *gpe_register_info; | ||
120 | acpi_status status; | 161 | acpi_status status; |
121 | 162 | ||
122 | ACPI_FUNCTION_ENTRY(); | 163 | ACPI_FUNCTION_ENTRY(); |
123 | 164 | ||
124 | /* Get the info block for the entire GPE register */ | 165 | status = acpi_hw_low_set_gpe(gpe_event_info, ACPI_GPE_COND_ENABLE); |
125 | |||
126 | gpe_register_info = gpe_event_info->register_info; | ||
127 | if (!gpe_register_info) { | ||
128 | return (AE_NOT_EXIST); | ||
129 | } | ||
130 | |||
131 | /* Write the entire GPE (runtime) enable register */ | ||
132 | |||
133 | status = acpi_hw_write(gpe_register_info->enable_for_run, | ||
134 | &gpe_register_info->enable_address); | ||
135 | |||
136 | return (status); | 166 | return (status); |
137 | } | 167 | } |
138 | 168 | ||
@@ -150,21 +180,28 @@ acpi_hw_write_gpe_enable_reg(struct acpi_gpe_event_info * gpe_event_info) | |||
150 | 180 | ||
151 | acpi_status acpi_hw_clear_gpe(struct acpi_gpe_event_info * gpe_event_info) | 181 | acpi_status acpi_hw_clear_gpe(struct acpi_gpe_event_info * gpe_event_info) |
152 | { | 182 | { |
183 | struct acpi_gpe_register_info *gpe_register_info; | ||
153 | acpi_status status; | 184 | acpi_status status; |
154 | u8 register_bit; | 185 | u32 register_bit; |
155 | 186 | ||
156 | ACPI_FUNCTION_ENTRY(); | 187 | ACPI_FUNCTION_ENTRY(); |
157 | 188 | ||
158 | register_bit = (u8)(1 << | 189 | /* Get the info block for the entire GPE register */ |
159 | (gpe_event_info->gpe_number - | 190 | |
160 | gpe_event_info->register_info->base_gpe_number)); | 191 | gpe_register_info = gpe_event_info->register_info; |
192 | if (!gpe_register_info) { | ||
193 | return (AE_NOT_EXIST); | ||
194 | } | ||
195 | |||
196 | register_bit = acpi_hw_gpe_register_bit(gpe_event_info, | ||
197 | gpe_register_info); | ||
161 | 198 | ||
162 | /* | 199 | /* |
163 | * Write a one to the appropriate bit in the status register to | 200 | * Write a one to the appropriate bit in the status register to |
164 | * clear this GPE. | 201 | * clear this GPE. |
165 | */ | 202 | */ |
166 | status = acpi_hw_write(register_bit, | 203 | status = acpi_hw_write(register_bit, |
167 | &gpe_event_info->register_info->status_address); | 204 | &gpe_register_info->status_address); |
168 | 205 | ||
169 | return (status); | 206 | return (status); |
170 | } | 207 | } |
@@ -187,7 +224,7 @@ acpi_hw_get_gpe_status(struct acpi_gpe_event_info * gpe_event_info, | |||
187 | acpi_event_status * event_status) | 224 | acpi_event_status * event_status) |
188 | { | 225 | { |
189 | u32 in_byte; | 226 | u32 in_byte; |
190 | u8 register_bit; | 227 | u32 register_bit; |
191 | struct acpi_gpe_register_info *gpe_register_info; | 228 | struct acpi_gpe_register_info *gpe_register_info; |
192 | acpi_status status; | 229 | acpi_status status; |
193 | acpi_event_status local_event_status = 0; | 230 | acpi_event_status local_event_status = 0; |
@@ -204,9 +241,8 @@ acpi_hw_get_gpe_status(struct acpi_gpe_event_info * gpe_event_info, | |||
204 | 241 | ||
205 | /* Get the register bitmask for this GPE */ | 242 | /* Get the register bitmask for this GPE */ |
206 | 243 | ||
207 | register_bit = (u8)(1 << | 244 | register_bit = acpi_hw_gpe_register_bit(gpe_event_info, |
208 | (gpe_event_info->gpe_number - | 245 | gpe_register_info); |
209 | gpe_event_info->register_info->base_gpe_number)); | ||
210 | 246 | ||
211 | /* GPE currently enabled? (enabled for runtime?) */ | 247 | /* GPE currently enabled? (enabled for runtime?) */ |
212 | 248 | ||