blob: 71aaceaf15902ad578e6d7302f1e2dc3610e1b41 [file] [log] [blame]
Duncan Laurie7522dc32016-05-10 20:20:16 -07001/*
2 * This file is part of the coreboot project.
3 *
4 * Copyright 2016 Google Inc.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 */
15
16#include <arch/acpi.h>
17#include <arch/acpi_device.h>
18#include <arch/acpigen.h>
19#include <console/console.h>
20#include <device/i2c.h>
21#include <device/device.h>
22#include <device/path.h>
23#include <stdint.h>
24#include <string.h>
25#include "chip.h"
26
27#if IS_ENABLED(CONFIG_HAVE_ACPI_TABLES)
28
29#define NAU8825_ACPI_NAME "NAU8"
30#define NAU8825_ACPI_HID "10508825"
31#define NAU8825_DP_INT(key,val) acpi_dp_write_integer("nuvoton," key, (val))
32
33static void nau8825_fill_ssdt(struct device *dev)
34{
35 struct drivers_i2c_nau8825_config *config = dev->chip_info;
36 const char *scope = acpi_device_scope(dev);
37 struct acpi_i2c i2c = {
38 .address = dev->path.i2c.device,
39 .mode_10bit = dev->path.i2c.mode_10bit,
40 .speed = config->bus_speed ? : I2C_SPEED_FAST,
41 .resource = scope,
42 };
43
44 if (!dev->enabled || !scope)
45 return;
46 if (config->sar_threshold_num > NAU8825_MAX_BUTTONS)
47 return;
48
49 /* Device */
50 acpigen_write_scope(scope);
51 acpigen_write_device(acpi_device_name(dev));
52 acpigen_write_name_string("_HID", NAU8825_ACPI_HID);
53 acpigen_write_name_integer("_UID", 0);
54 acpigen_write_name_string("_DDN", dev->chip_ops->name);
55 acpigen_write_STA(ACPI_STATUS_DEVICE_ALL_ON);
56
57 /* Resources */
58 acpigen_write_name("_CRS");
59 acpigen_write_resourcetemplate_header();
60 acpi_device_write_i2c(&i2c);
61 acpi_device_write_interrupt(&config->irq);
62 acpigen_write_resourcetemplate_footer();
63
64 /* Device Properties */
65 acpi_dp_write_header();
66 NAU8825_DP_INT("jkdet-enable", config->jkdet_enable);
67 NAU8825_DP_INT("jkdet-pull-enable", config->jkdet_pull_enable);
68 NAU8825_DP_INT("jkdet-pull-up", config->jkdet_pull_up);
69 NAU8825_DP_INT("jkdet-polarity", config->jkdet_polarity);
70 NAU8825_DP_INT("vref-impedance", config->vref_impedance);
71 NAU8825_DP_INT("micbias-voltage", config->micbias_voltage);
72 NAU8825_DP_INT("sar-hysteresis", config->sar_hysteresis);
73 NAU8825_DP_INT("sar-voltage", config->sar_voltage);
74 NAU8825_DP_INT("sar-compare-time", config->sar_compare_time);
75 NAU8825_DP_INT("sar-sampling-time", config->sar_sampling_time);
76 NAU8825_DP_INT("short-key-debounce", config->short_key_debounce);
77 NAU8825_DP_INT("jack-insert-debounce", config->jack_insert_debounce);
78 NAU8825_DP_INT("jack-eject-deboune", config->jack_eject_debounce);
79 NAU8825_DP_INT("sar-threshold-num", config->sar_threshold_num);
80 acpi_dp_write_integer_array("nuvoton,sar-threshold",
81 config->sar_threshold,
82 config->sar_threshold_num);
83 acpi_dp_write_footer();
84
85 acpigen_pop_len(); /* Device */
86 acpigen_pop_len(); /* Scope */
87
88 printk(BIOS_INFO, "%s: %s address 0%xh irq %d\n",
89 acpi_device_path(dev), dev->chip_ops->name,
90 dev->path.i2c.device, config->irq.pin);
91}
92
93static const char *nau8825_acpi_name(struct device *dev)
94{
95 return NAU8825_ACPI_NAME;
96}
97#endif
98
99static struct device_operations nau8825_ops = {
100 .read_resources = DEVICE_NOOP,
101 .set_resources = DEVICE_NOOP,
102 .enable_resources = DEVICE_NOOP,
103#if IS_ENABLED(CONFIG_HAVE_ACPI_TABLES)
104 .acpi_name = &nau8825_acpi_name,
105 .acpi_fill_ssdt_generator = &nau8825_fill_ssdt,
106#endif
107};
108
109static void nau8825_enable(struct device *dev)
110{
111 dev->ops = &nau8825_ops;
112}
113
114struct chip_operations drivers_i2c_nau8825_ops = {
115 CHIP_NAME("Nuvoton NAU8825 Codec")
116 .enable_dev = &nau8825_enable
117};