Revert "ARM: tegra: tegratab: dummy change"
[linux-2.6.git] / drivers / edp / psy_depletion.c
1 /*
2  * Copyright (c) 2013, NVIDIA CORPORATION.  All rights reserved.
3  *
4  * This program is free software; you can redistribute it and/or modify it
5  * under the terms and conditions of the GNU General Public License,
6  * version 2, as published by the Free Software Foundation.
7  *
8  * This program is distributed in the hope it will be useful, but WITHOUT
9  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
11  * more details.
12  *
13  * You should have received a copy of the GNU General Public License
14  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
15  */
16
17 #include <linux/debugfs.h>
18 #include <linux/edp.h>
19 #include <linux/edpdev.h>
20 #include <linux/kernel.h>
21 #include <linux/module.h>
22 #include <linux/platform_device.h>
23 #include <linux/power_supply.h>
24 #include <linux/slab.h>
25 #include <linux/workqueue.h>
26
27 #define DEPL_INTERVAL   60000
28
29 struct depl_driver {
30         struct edp_client client;
31         struct psy_depletion_platform_data *pdata;
32         struct delayed_work work;
33         struct edp_manager *manager;
34         struct power_supply *psy;
35         bool emulator_mode;
36         int capacity;
37         int (*get_ocv)(struct depl_driver *drv, unsigned int capacity);
38 };
39
40 static int depl_psy_get_property(struct depl_driver *drv,
41                 enum power_supply_property psp, int *val)
42 {
43         union power_supply_propval pv;
44
45         if (!drv->psy)
46                 return -ENODEV;
47         if (drv->psy->get_property(drv->psy, psp, &pv))
48                 return -EFAULT;
49         if (val)
50                 *val = pv.intval;
51         return 0;
52 }
53
54 static int depl_psy_ocv_from_chip(struct depl_driver *drv,
55                 unsigned int capacity)
56 {
57         int val;
58         if (depl_psy_get_property(drv, POWER_SUPPLY_PROP_VOLTAGE_OCV, &val))
59                 return drv->pdata->vsys_min;
60         return val;
61 }
62
63 static int depl_psy_capacity(struct depl_driver *drv)
64 {
65         int val;
66         if (drv->emulator_mode)
67                 return drv->capacity;
68         if (depl_psy_get_property(drv, POWER_SUPPLY_PROP_CAPACITY, &val))
69                 return 0;
70         return val;
71 }
72
73 static unsigned int depl_psy_temp(struct depl_driver *drv)
74 {
75         int val;
76         if (depl_psy_get_property(drv, POWER_SUPPLY_PROP_TEMP, &val))
77                 return 25;
78         return max(0, val);
79 }
80
81 static inline unsigned int depl_maximum(struct depl_driver *drv)
82 {
83         return drv->client.states[0];
84 }
85
86 /* Given two points (x1, y1) and (x2, y2), find the y coord of x */
87 static int depl_interpolate(int x, int x1, int y1, int x2, int y2)
88 {
89         if (x1 == x2)
90                 return y1;
91         return (y2 * (x - x1) - y1 * (x - x2)) / (x2 - x1);
92 }
93
94 static int depl_psy_ocv_from_lut(struct depl_driver *drv,
95                 unsigned int capacity)
96 {
97         struct psy_depletion_ocv_lut *p;
98         struct psy_depletion_ocv_lut *q;
99
100         p = drv->pdata->ocv_lut;
101
102         while (p->capacity > capacity)
103                 p++;
104
105         if (p == drv->pdata->ocv_lut)
106                 return p->ocv;
107
108         q = p - 1;
109
110         return depl_interpolate(capacity, p->capacity, p->ocv, q->capacity,
111                         q->ocv);
112 }
113
114 /* Calc RBAT for current capacity (SOC) */
115 static int depl_rbat(struct depl_driver *drv, unsigned int capacity)
116 {
117         struct psy_depletion_rbat_lut *p;
118         struct psy_depletion_rbat_lut *q;
119         int rbat;
120
121         rbat = drv->pdata->r_const;
122         p = drv->pdata->rbat_lut;
123         if (!p)
124                 return rbat;
125
126         while (p->capacity > capacity)
127                 p++;
128
129         if (p == drv->pdata->rbat_lut)
130                 return rbat + p->rbat;
131
132         q = p - 1;
133
134         rbat += depl_interpolate(capacity, p->capacity, p->rbat,
135                         q->capacity, q->rbat);
136         return rbat;
137 }
138
139 static s64 depl_ibat_possible(struct depl_driver *drv, s64 ocv, s64 rbat)
140 {
141         return div64_s64(1000 * (ocv - drv->pdata->vsys_min), rbat);
142 }
143
144 /* Calc IBAT for a given temperature */
145 static int depl_ibat(struct depl_driver *drv, unsigned int temp)
146 {
147         struct psy_depletion_ibat_lut *p;
148         struct psy_depletion_ibat_lut *q;
149         int ibat;
150
151         p = drv->pdata->ibat_lut;
152         while (p->ibat && p->temp > temp)
153                 p++;
154
155         if (p == drv->pdata->ibat_lut || !p->ibat)
156                 return p->ibat;
157
158         q = p - 1;
159         ibat = depl_interpolate(temp, p->temp, p->ibat, q->temp, q->ibat);
160
161         return ibat;
162 }
163
164 static s64 depl_pbat(s64 ocv, s64 ibat, s64 rbat)
165 {
166         s64 pbat;
167         pbat = ocv - div64_s64(ibat * rbat, 1000);
168         pbat = div64_s64(pbat * ibat, 1000000);
169         return pbat;
170 }
171
172 static unsigned int depl_calc(struct depl_driver *drv)
173 {
174         unsigned int capacity;
175         s64 ocv;
176         s64 rbat;
177         s64 ibat_pos;
178         s64 ibat_tbat;
179         s64 ibat_lcm;
180         s64 pbat_lcm;
181         s64 pbat_nom;
182         s64 pbat_gain;
183         s64 depl;
184
185         capacity = depl_psy_capacity(drv);
186         if (capacity >= 100)
187                 return 0;
188
189         ocv = drv->get_ocv(drv, capacity);
190         rbat = depl_rbat(drv, capacity);
191
192         ibat_pos = depl_ibat_possible(drv, ocv, rbat);
193         ibat_tbat = depl_ibat(drv, depl_psy_temp(drv));
194         ibat_lcm = min(ibat_pos, ibat_tbat);
195
196         pbat_lcm = depl_pbat(ocv, ibat_lcm, rbat);
197         pbat_nom = depl_pbat(drv->pdata->vcharge, drv->pdata->ibat_nom, rbat);
198         pbat_gain = div64_s64(drv->manager->max * 1000, pbat_nom);
199
200         depl = drv->manager->max - div64_s64(pbat_gain * pbat_lcm, 1000);
201
202         pr_debug("capacity : %u\n", capacity);
203         pr_debug("ocv      : %lld\n", ocv);
204         pr_debug("rbat     : %lld\n", rbat);
205         pr_debug("ibat_pos : %lld\n", ibat_pos);
206         pr_debug("ibat_tbat: %lld\n", ibat_tbat);
207         pr_debug("ibat_lcm : %lld\n", ibat_lcm);
208         pr_debug("pbat_lcm : %lld\n", pbat_lcm);
209         pr_debug("pbat_nom : %lld\n", pbat_nom);
210         pr_debug("pbat_gain: %lld\n", pbat_gain);
211         pr_debug("depletion: %lld\n", depl);
212
213         depl = clamp_t(s64, depl, 0, depl_maximum(drv));
214         return depl;
215 }
216
217 static void depl_update(struct work_struct *work)
218 {
219         struct depl_driver *drv;
220         struct edp_client *c;
221         unsigned int depl;
222         unsigned int i;
223
224         drv = container_of(work, struct depl_driver, work.work);
225         c = &drv->client;
226         depl = depl_calc(drv);
227
228         i = c->num_states - 1;
229         while (i && c->states[i] < depl)
230                 i--;
231
232         edp_update_client_request(c, i, NULL);
233
234         schedule_delayed_work(to_delayed_work(work),
235                         msecs_to_jiffies(DEPL_INTERVAL));
236 }
237
238 /* Nothing to do */
239 static void depl_edp_callback(unsigned int new_state, void *priv_data)
240 {
241 }
242
243 static void depl_shutdown(struct platform_device *pdev)
244 {
245         struct depl_driver *drv = platform_get_drvdata(pdev);
246         cancel_delayed_work_sync(&drv->work);
247 }
248
249 static int depl_suspend(struct platform_device *pdev, pm_message_t state)
250 {
251         depl_shutdown(pdev);
252         return 0;
253 }
254
255 static int depl_resume(struct platform_device *pdev)
256 {
257         struct depl_driver *drv = platform_get_drvdata(pdev);
258         schedule_delayed_work(&drv->work, 0);
259         return 0;
260 }
261
262 static __devinit int depl_init_ocv_reader(struct depl_driver *drv)
263 {
264         if (!depl_psy_get_property(drv, POWER_SUPPLY_PROP_VOLTAGE_OCV, NULL))
265                 drv->get_ocv = depl_psy_ocv_from_chip;
266         else if (drv->pdata->ocv_lut)
267                 drv->get_ocv = depl_psy_ocv_from_lut;
268         else
269                 return -ENODEV;
270
271         return 0;
272 }
273
274 #ifdef CONFIG_DEBUG_FS
275 static int capacity_set(void *data, u64 val)
276 {
277         struct depl_driver *drv = data;
278
279         drv->capacity = clamp_t(int, val, 0, 100);
280         flush_delayed_work_sync(&drv->work);
281
282         return 0;
283 }
284
285 static int capacity_get(void *data, u64 *val)
286 {
287         struct depl_driver *drv = data;
288         *val = drv->capacity;
289         return 0;
290 }
291
292 static int vsysmin_set(void *data, u64 val)
293 {
294         struct depl_driver *drv = data;
295
296         drv->pdata->vsys_min = val;
297         flush_delayed_work_sync(&drv->work);
298
299         return 0;
300 }
301
302 static int vsysmin_get(void *data, u64 *val)
303 {
304         struct depl_driver *drv = data;
305         *val = drv->pdata->vsys_min;
306         return 0;
307 }
308
309 DEFINE_SIMPLE_ATTRIBUTE(capacity_fops, capacity_get, capacity_set, "%lld\n");
310 DEFINE_SIMPLE_ATTRIBUTE(vsysmin_fops, vsysmin_get, vsysmin_set, "%lld\n");
311
312 static void init_debug(struct depl_driver *drv)
313 {
314         struct dentry *d;
315
316         if (!drv->client.dentry) {
317                 WARN_ON(1);
318                 return;
319         }
320
321         d = debugfs_create_file("vsys_min", S_IRUGO | S_IWUSR,
322                         drv->client.dentry, drv, &vsysmin_fops);
323         WARN_ON(IS_ERR_OR_NULL(d));
324
325         if (!drv->emulator_mode)
326                 return;
327
328         d = debugfs_create_file("capacity", S_IRUGO | S_IWUSR,
329                         drv->client.dentry, drv, &capacity_fops);
330         WARN_ON(IS_ERR_OR_NULL(d));
331 }
332 #else
333 static inline void init_debug(struct depl_driver *drv) {}
334 #endif
335
336 static __devinit int depl_probe(struct platform_device *pdev)
337 {
338         struct depl_driver *drv;
339         struct edp_manager *m;
340         struct edp_client *c;
341         int r = -EFAULT;
342
343         if (!pdev->dev.platform_data)
344                 return -EINVAL;
345
346         m = edp_get_manager("battery");
347         if (!m) {
348                 dev_err(&pdev->dev, "could not get EDP manager\n");
349                 return -ENODEV;
350         }
351
352         drv = devm_kzalloc(&pdev->dev, sizeof(*drv), GFP_KERNEL);
353         if (!drv)
354                 return -ENOMEM;
355
356         drv->pdata = pdev->dev.platform_data;
357         drv->manager = m;
358         drv->psy = power_supply_get_by_name(drv->pdata->power_supply);
359         if (!drv->psy) {
360                 if (!drv->pdata->ocv_lut)
361                         goto fail;
362                 drv->capacity = 100;
363                 drv->emulator_mode = true;
364         }
365
366         r = depl_init_ocv_reader(drv);
367         if (r)
368                 goto fail;
369
370         c = &drv->client;
371         strncpy(c->name, "depletion", EDP_NAME_LEN - 1);
372         c->name[EDP_NAME_LEN - 1] = 0;
373         c->priority = EDP_MAX_PRIO;
374         c->throttle = depl_edp_callback;
375         c->notify_promotion = depl_edp_callback;
376         c->states = drv->pdata->states;
377         c->num_states = drv->pdata->num_states;
378         c->e0_index = drv->pdata->e0_index;
379
380         r = edp_register_client(m, c);
381         if (r) {
382                 dev_err(&pdev->dev, "failed to register: %d\n", r);
383                 goto fail;
384         }
385
386         platform_set_drvdata(pdev, drv);
387         INIT_DELAYED_WORK_DEFERRABLE(&drv->work, depl_update);
388         schedule_delayed_work(&drv->work, 0);
389
390         init_debug(drv);
391
392         return 0;
393
394 fail:
395         devm_kfree(&pdev->dev, drv);
396         return r;
397 }
398
399 static struct platform_driver depl_driver = {
400         .probe = depl_probe,
401         .shutdown = depl_shutdown,
402         .suspend = depl_suspend,
403         .resume = depl_resume,
404         .driver = {
405                 .name = "psy_depletion",
406                 .owner = THIS_MODULE
407         }
408 };
409
410 static __init int depl_init(void)
411 {
412         return platform_driver_register(&depl_driver);
413 }
414 late_initcall(depl_init);