From: Kuo-Jung Su <dant...@faraday-tech.com>

Signed-off-by: Kuo-Jung Su <dant...@faraday-tech.com>
---
 hw/Makefile.objs           |    1 +
 hw/arm/spitz.c             |    9 +++--
 hw/arm/z2.c                |    9 +++--
 hw/audio_codec.c           |   81 +++++++++++++++++++++++++++++++++++++++
 hw/audio_codec.h           |   56 +++++++++++++++++++++++++++
 hw/i2c.h                   |    9 -----
 hw/marvell_88w8618_audio.c |   23 +++++++----
 hw/wm8750.c                |   91 ++++++++++++++++++++++----------------------
 8 files changed, 211 insertions(+), 68 deletions(-)
 create mode 100644 hw/audio_codec.c
 create mode 100644 hw/audio_codec.h

diff --git a/hw/Makefile.objs b/hw/Makefile.objs
index eb7eb31..aafcac5 100644
--- a/hw/Makefile.objs
+++ b/hw/Makefile.objs
@@ -167,6 +167,7 @@ common-obj-$(CONFIG_REALLY_VIRTFS) += 9pfs/
 common-obj-y += usb/
 common-obj-$(CONFIG_PTIMER) += ptimer.o
 common-obj-$(CONFIG_MAX7310) += max7310.o
+common-obj-y += audio_codec.o
 common-obj-$(CONFIG_WM8750) += wm8750.o
 common-obj-$(CONFIG_TWL92230) += twl92230.o
 common-obj-$(CONFIG_TSC2005) += tsc2005.o
diff --git a/hw/arm/spitz.c b/hw/arm/spitz.c
index f5832be..618968b 100644
--- a/hw/arm/spitz.c
+++ b/hw/arm/spitz.c
@@ -24,6 +24,7 @@
 #include "ui/console.h"
 #include "block/block.h"
 #include "audio/audio.h"
+#include "hw/audio_codec.h"
 #include "hw/boards.h"
 #include "sysemu/blockdev.h"
 #include "hw/sysbus.h"
@@ -739,9 +740,11 @@ static void spitz_i2c_setup(PXA2xxState *cpu)
                     qemu_allocate_irqs(spitz_wm8750_addr, wm, 1)[0]);
     /* .. and to the sound interface.  */
     cpu->i2s->opaque = wm;
-    cpu->i2s->codec_out = wm8750_dac_dat;
-    cpu->i2s->codec_in = wm8750_adc_dat;
-    wm8750_data_req_set(wm, cpu->i2s->data_req, cpu->i2s);
+    cpu->i2s->codec_out = audio_codec_dac_dat;
+    cpu->i2s->codec_in = audio_codec_adc_dat;
+    audio_codec_data_req_set(DEVICE(wm),
+                             cpu->i2s->data_req,
+                             cpu->i2s);
 }
 
 static void spitz_akita_i2c_setup(PXA2xxState *cpu)
diff --git a/hw/arm/z2.c b/hw/arm/z2.c
index cbb6d80..bc11309 100644
--- a/hw/arm/z2.c
+++ b/hw/arm/z2.c
@@ -23,6 +23,7 @@
 #include "sysemu/blockdev.h"
 #include "ui/console.h"
 #include "audio/audio.h"
+#include "hw/audio_codec.h"
 #include "exec/address-spaces.h"
 
 #ifdef DEBUG_Z2
@@ -353,9 +354,11 @@ static void z2_init(QEMUMachineInitArgs *args)
     i2c_create_slave(bus, "aer915", 0x55);
     wm = i2c_create_slave(bus, "wm8750", 0x1b);
     mpu->i2s->opaque = wm;
-    mpu->i2s->codec_out = wm8750_dac_dat;
-    mpu->i2s->codec_in = wm8750_adc_dat;
-    wm8750_data_req_set(wm, mpu->i2s->data_req, mpu->i2s);
+    mpu->i2s->codec_out = audio_codec_dac_dat;
+    mpu->i2s->codec_in = audio_codec_adc_dat;
+    audio_codec_data_req_set(DEVICE(wm),
+                             mpu->i2s->data_req,
+                             mpu->i2s);
 
     qdev_connect_gpio_out(mpu->gpio, Z2_GPIO_LCD_CS,
         qemu_allocate_irqs(z2_lcd_cs, z2_lcd, 1)[0]);
diff --git a/hw/audio_codec.c b/hw/audio_codec.c
new file mode 100644
index 0000000..c62e51f
--- /dev/null
+++ b/hw/audio_codec.c
@@ -0,0 +1,81 @@
+/*
+ * Audio Codec Class
+ *
+ * Copyright (c) 2013 Faraday Technology
+ * Written by Dante Su <dant...@faraday-tech.com>
+ *
+ * This file is licensed under GNU GPL v2+.
+ */
+
+#include "qdev.h"
+#include "i2c.h"
+#include "audio_codec.h"
+
+void audio_codec_data_req_set(DeviceState *dev,
+                              void (*data_req)(void *, int, int),
+                              void *opaque)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(dev);
+    if (k->data_req_set) {
+        k->data_req_set(dev, data_req, opaque);
+    }
+}
+
+void audio_codec_dac_dat(void *opaque, uint32_t sample)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(opaque);
+    if (k->dac_dat) {
+        k->dac_dat(opaque, sample);
+    }
+}
+
+uint32_t audio_codec_adc_dat(void *opaque)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(opaque);
+    uint32_t ret = 0;
+    if (k->adc_dat) {
+        ret = k->adc_dat(opaque);
+    }
+    return ret;
+}
+
+void *audio_codec_dac_buffer(void *opaque, int samples)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(opaque);
+    void *ret = NULL;
+    if (k->dac_buffer) {
+        ret = k->dac_buffer(opaque, samples);
+    }
+    return ret;
+}
+
+void audio_codec_dac_commit(void *opaque)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(opaque);
+    if (k->dac_commit) {
+        k->dac_commit(opaque);
+    }
+}
+
+void audio_codec_set_bclk_in(void *opaque, int new_hz)
+{
+    AudioCodecClass *k = AUDIO_CODEC_GET_CLASS(opaque);
+    if (k->set_bclk_in) {
+        k->set_bclk_in(opaque, new_hz);
+    }
+}
+
+static const TypeInfo audio_codec_info = {
+    .name          = TYPE_AUDIO_CODEC,
+    .parent        = TYPE_I2C_SLAVE,
+    .instance_size = sizeof(AudioCodecState),
+    .abstract      = true,
+    .class_size    = sizeof(AudioCodecClass),
+};
+
+static void audio_codec_register_types(void)
+{
+    type_register_static(&audio_codec_info);
+}
+
+type_init(audio_codec_register_types)
diff --git a/hw/audio_codec.h b/hw/audio_codec.h
new file mode 100644
index 0000000..25a2743
--- /dev/null
+++ b/hw/audio_codec.h
@@ -0,0 +1,56 @@
+/*
+ * Audio Codec Class
+ *
+ * Copyright (c) 2013 Faraday Technology
+ * Written by Dante Su <dant...@faraday-tech.com>
+ *
+ * This file is licensed under GNU GPL v2+.
+ */
+
+#ifndef QEMU_AUDIO_CODEC_H
+#define QEMU_AUDIO_CODEC_H
+
+#include "qdev.h"
+#include "i2c.h"
+
+typedef I2CSlave    AudioCodecState;
+
+#define TYPE_AUDIO_CODEC "audio-codec"
+#define AUDIO_CODEC(obj) \
+     OBJECT_CHECK(AudioCodecState, (obj), TYPE_AUDIO_CODEC)
+
+typedef struct AudioCodecClass {
+    /*< private >*/
+    I2CSlaveClass parent;
+
+    /*< public >*/
+    void     (*data_req_set)(DeviceState *dev,
+                             void (*data_req)(void *, int, int),
+                             void *opaque);
+    void     (*dac_dat)(void *opaque, uint32_t sample);
+    uint32_t (*adc_dat)(void *opaque);
+    void    *(*dac_buffer)(void *opaque, int samples);
+    void     (*dac_commit)(void *opaque);
+    void     (*set_bclk_in)(void *opaque, int new_hz);
+} AudioCodecClass;
+
+#define AUDIO_CODEC_CLASS(klass) \
+     OBJECT_CLASS_CHECK(AudioCodecClass, (klass), TYPE_AUDIO_CODEC)
+#define AUDIO_CODEC_GET_CLASS(obj) \
+     OBJECT_GET_CLASS(AudioCodecClass, (obj), TYPE_AUDIO_CODEC)
+
+void audio_codec_data_req_set(DeviceState *dev,
+                              void (*data_req)(void *, int, int),
+                              void *opaque);
+
+void audio_codec_dac_dat(void *opaque, uint32_t sample);
+
+uint32_t audio_codec_adc_dat(void *opaque);
+
+void *audio_codec_dac_buffer(void *opaque, int samples);
+
+void audio_codec_dac_commit(void *opaque);
+
+void audio_codec_set_bclk_in(void *opaque, int new_hz);
+
+#endif
diff --git a/hw/i2c.h b/hw/i2c.h
index 461392f..39566b5 100644
--- a/hw/i2c.h
+++ b/hw/i2c.h
@@ -63,15 +63,6 @@ int i2c_recv(i2c_bus *bus);
 
 DeviceState *i2c_create_slave(i2c_bus *bus, const char *name, uint8_t addr);
 
-/* wm8750.c */
-void wm8750_data_req_set(DeviceState *dev,
-                void (*data_req)(void *, int, int), void *opaque);
-void wm8750_dac_dat(void *opaque, uint32_t sample);
-uint32_t wm8750_adc_dat(void *opaque);
-void *wm8750_dac_buffer(void *opaque, int samples);
-void wm8750_dac_commit(void *opaque);
-void wm8750_set_bclk_in(void *opaque, int new_hz);
-
 /* lm832x.c */
 void lm832x_key_event(DeviceState *dev, int key, int state);
 
diff --git a/hw/marvell_88w8618_audio.c b/hw/marvell_88w8618_audio.c
index e042046..85986e1 100644
--- a/hw/marvell_88w8618_audio.c
+++ b/hw/marvell_88w8618_audio.c
@@ -14,6 +14,7 @@
 #include "hw/i2c.h"
 #include "hw/sysbus.h"
 #include "audio/audio.h"
+#include "audio_codec.h"
 
 #define MP_AUDIO_SIZE           0x00001000
 
@@ -82,32 +83,36 @@ static void mv88w8618_audio_callback(void *opaque, int 
free_out, int free_in)
     mem_buffer = buf;
     if (s->playback_mode & MP_AUDIO_16BIT_SAMPLE) {
         if (s->playback_mode & MP_AUDIO_MONO) {
-            codec_buffer = wm8750_dac_buffer(s->wm, block_size >> 1);
+            codec_buffer = audio_codec_dac_buffer(AUDIO_CODEC(s->wm),
+                                                  block_size >> 1);
             for (pos = 0; pos < block_size; pos += 2) {
                 *codec_buffer++ = *(int16_t *)mem_buffer;
                 *codec_buffer++ = *(int16_t *)mem_buffer;
                 mem_buffer += 2;
             }
         } else {
-            memcpy(wm8750_dac_buffer(s->wm, block_size >> 2),
-                   (uint32_t *)mem_buffer, block_size);
+            memcpy(audio_codec_dac_buffer(AUDIO_CODEC(s->wm),
+                                          block_size >> 2),
+                   (uint32_t *)mem_buffer,
+                   block_size);
         }
     } else {
         if (s->playback_mode & MP_AUDIO_MONO) {
-            codec_buffer = wm8750_dac_buffer(s->wm, block_size);
+            codec_buffer = audio_codec_dac_buffer(s->wm, block_size);
             for (pos = 0; pos < block_size; pos++) {
                 *codec_buffer++ = cpu_to_le16(256 * *mem_buffer);
                 *codec_buffer++ = cpu_to_le16(256 * *mem_buffer++);
             }
         } else {
-            codec_buffer = wm8750_dac_buffer(s->wm, block_size >> 1);
+            codec_buffer = audio_codec_dac_buffer(AUDIO_CODEC(s->wm),
+                                                  block_size >> 1);
             for (pos = 0; pos < block_size; pos += 2) {
                 *codec_buffer++ = cpu_to_le16(256 * *mem_buffer++);
                 *codec_buffer++ = cpu_to_le16(256 * *mem_buffer++);
             }
         }
     }
-    wm8750_dac_commit(s->wm);
+    audio_codec_dac_commit(AUDIO_CODEC(s->wm));
 
     s->last_free = free_out - block_size;
 
@@ -135,7 +140,7 @@ static void 
mv88w8618_audio_clock_update(mv88w8618_audio_state *s)
     }
     rate /= ((s->clock_div >> 8) & 0xff) + 1;
 
-    wm8750_set_bclk_in(s->wm, rate);
+    audio_codec_set_bclk_in(AUDIO_CODEC(s->wm), rate);
 }
 
 static uint64_t mv88w8618_audio_read(void *opaque, hwaddr offset,
@@ -244,7 +249,9 @@ static int mv88w8618_audio_init(SysBusDevice *dev)
 
     sysbus_init_irq(dev, &s->irq);
 
-    wm8750_data_req_set(s->wm, mv88w8618_audio_callback, s);
+    audio_codec_data_req_set(DEVICE(s->wm),
+                             mv88w8618_audio_callback,
+                             s);
 
     memory_region_init_io(&s->iomem, &mv88w8618_audio_ops, s,
                           "audio", MP_AUDIO_SIZE);
diff --git a/hw/wm8750.c b/hw/wm8750.c
index 0904cf4..fae274b 100644
--- a/hw/wm8750.c
+++ b/hw/wm8750.c
@@ -10,11 +10,12 @@
 #include "hw/hw.h"
 #include "hw/i2c.h"
 #include "audio/audio.h"
+#include "audio_codec.h"
 
 #define IN_PORT_N      3
 #define OUT_PORT_N     3
 
-#define CODEC          "wm8750"
+#define TYPE_WM8750 "wm8750"
 
 typedef struct {
     int adc;
@@ -24,7 +25,7 @@ typedef struct {
 } WMRate;
 
 typedef struct {
-    I2CSlave i2c;
+    AudioCodecState parent;
     uint8_t i2c_data[2];
     int i2c_len;
     QEMUSoundCard card;
@@ -50,6 +51,9 @@ typedef struct {
     int adc_hz, dac_hz, ext_adc_hz, ext_dac_hz, master;
 } WM8750State;
 
+#define WM8750(obj) \
+    OBJECT_CHECK(WM8750State, obj, TYPE_WM8750)
+
 /* pow(10.0, -i / 20.0) * 255, i = 0..42 */
 static const uint8_t wm8750_vol_db_table[] = {
     255, 227, 203, 181, 161, 143, 128, 114, 102, 90, 81, 72, 64, 57, 51, 45,
@@ -80,14 +84,14 @@ static inline void wm8750_out_flush(WM8750State *s)
 
 static void wm8750_audio_in_cb(void *opaque, int avail_b)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
     s->req_in = avail_b;
     s->data_req(s->opaque, s->req_out >> 2, avail_b >> 2);
 }
 
 static void wm8750_audio_out_cb(void *opaque, int free_b)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
 
     if (s->idx_out >= free_b) {
         s->idx_out = free_b;
@@ -200,11 +204,11 @@ static void wm8750_set_format(WM8750State *s)
     in_fmt.fmt = AUD_FMT_S16;
 
     s->adc_voice[0] = AUD_open_in(&s->card, s->adc_voice[0],
-                    CODEC ".input1", s, wm8750_audio_in_cb, &in_fmt);
+                    TYPE_WM8750 ".input1", s, wm8750_audio_in_cb, &in_fmt);
     s->adc_voice[1] = AUD_open_in(&s->card, s->adc_voice[1],
-                    CODEC ".input2", s, wm8750_audio_in_cb, &in_fmt);
+                    TYPE_WM8750 ".input2", s, wm8750_audio_in_cb, &in_fmt);
     s->adc_voice[2] = AUD_open_in(&s->card, s->adc_voice[2],
-                    CODEC ".input3", s, wm8750_audio_in_cb, &in_fmt);
+                    TYPE_WM8750 ".input3", s, wm8750_audio_in_cb, &in_fmt);
 
     /* Setup output */
     out_fmt.endianness = 0;
@@ -213,12 +217,12 @@ static void wm8750_set_format(WM8750State *s)
     out_fmt.fmt = AUD_FMT_S16;
 
     s->dac_voice[0] = AUD_open_out(&s->card, s->dac_voice[0],
-                    CODEC ".speaker", s, wm8750_audio_out_cb, &out_fmt);
+                    TYPE_WM8750 ".speaker", s, wm8750_audio_out_cb, &out_fmt);
     s->dac_voice[1] = AUD_open_out(&s->card, s->dac_voice[1],
-                    CODEC ".headphone", s, wm8750_audio_out_cb, &out_fmt);
+                    TYPE_WM8750 ".headphone", s, wm8750_audio_out_cb, 
&out_fmt);
     /* MONOMIX is also in stereo for simplicity */
     s->dac_voice[2] = AUD_open_out(&s->card, s->dac_voice[2],
-                    CODEC ".monomix", s, wm8750_audio_out_cb, &out_fmt);
+                    TYPE_WM8750 ".monomix", s, wm8750_audio_out_cb, &out_fmt);
     /* no sense emulating OUT3 which is a mix of other outputs */
 
     wm8750_vol_update(s);
@@ -256,7 +260,7 @@ static void wm8750_clk_update(WM8750State *s, int ext)
 
 static void wm8750_reset(I2CSlave *i2c)
 {
-    WM8750State *s = (WM8750State *) i2c;
+    WM8750State *s = WM8750(i2c);
     s->rate = &wm_rate_table[0];
     s->enable = 0;
     wm8750_clk_update(s, 1);
@@ -299,7 +303,7 @@ static void wm8750_reset(I2CSlave *i2c)
 
 static void wm8750_event(I2CSlave *i2c, enum i2c_event event)
 {
-    WM8750State *s = (WM8750State *) i2c;
+    WM8750State *s = WM8750(i2c);
 
     switch (event) {
     case I2C_START_SEND:
@@ -356,7 +360,7 @@ static void wm8750_event(I2CSlave *i2c, enum i2c_event 
event)
 
 static int wm8750_tx(I2CSlave *i2c, uint8_t data)
 {
-    WM8750State *s = (WM8750State *) i2c;
+    WM8750State *s = WM8750(i2c);
     uint8_t cmd;
     uint16_t value;
 
@@ -542,7 +546,7 @@ static int wm8750_tx(I2CSlave *i2c, uint8_t data)
         break;
 
     case WM8750_RESET: /* Reset */
-        wm8750_reset(&s->i2c);
+        wm8750_reset(I2C_SLAVE(&s->parent));
         break;
 
 #ifdef VERBOSE
@@ -561,21 +565,21 @@ static int wm8750_rx(I2CSlave *i2c)
 
 static void wm8750_pre_save(void *opaque)
 {
-    WM8750State *s = opaque;
+    WM8750State *s = WM8750(opaque);
 
     s->rate_vmstate = s->rate - wm_rate_table;
 }
 
 static int wm8750_post_load(void *opaque, int version_id)
 {
-    WM8750State *s = opaque;
+    WM8750State *s = WM8750(opaque);
 
     s->rate = &wm_rate_table[s->rate_vmstate & 0x1f];
     return 0;
 }
 
 static const VMStateDescription vmstate_wm8750 = {
-    .name = CODEC,
+    .name = TYPE_WM8750,
     .version_id = 0,
     .minimum_version_id = 0,
     .minimum_version_id_old = 0,
@@ -604,42 +608,31 @@ static const VMStateDescription vmstate_wm8750 = {
         VMSTATE_UINT8(format, WM8750State),
         VMSTATE_UINT8(power, WM8750State),
         VMSTATE_UINT8(rate_vmstate, WM8750State),
-        VMSTATE_I2C_SLAVE(i2c, WM8750State),
         VMSTATE_END_OF_LIST()
     }
 };
 
 static int wm8750_init(I2CSlave *i2c)
 {
-    WM8750State *s = FROM_I2C_SLAVE(WM8750State, i2c);
+    WM8750State *s = WM8750(i2c);
 
-    AUD_register_card(CODEC, &s->card);
-    wm8750_reset(&s->i2c);
+    AUD_register_card(TYPE_WM8750, &s->card);
+    wm8750_reset(I2C_SLAVE(&s->parent));
 
     return 0;
 }
 
-#if 0
-static void wm8750_fini(I2CSlave *i2c)
-{
-    WM8750State *s = (WM8750State *) i2c;
-    wm8750_reset(&s->i2c);
-    AUD_remove_card(&s->card);
-    g_free(s);
-}
-#endif
-
-void wm8750_data_req_set(DeviceState *dev,
+static void wm8750_data_req_set(DeviceState *dev,
                 void (*data_req)(void *, int, int), void *opaque)
 {
-    WM8750State *s = FROM_I2C_SLAVE(WM8750State, I2C_SLAVE(dev));
+    WM8750State *s = WM8750(dev);
     s->data_req = data_req;
     s->opaque = opaque;
 }
 
-void wm8750_dac_dat(void *opaque, uint32_t sample)
+static void wm8750_dac_dat(void *opaque, uint32_t sample)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
 
     *(uint32_t *) &s->data_out[s->idx_out] = sample;
     s->req_out -= 4;
@@ -648,9 +641,9 @@ void wm8750_dac_dat(void *opaque, uint32_t sample)
         wm8750_out_flush(s);
 }
 
-void *wm8750_dac_buffer(void *opaque, int samples)
+static void *wm8750_dac_buffer(void *opaque, int samples)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
     /* XXX: Should check if there are <i>samples</i> free samples available */
     void *ret = s->data_out + s->idx_out;
 
@@ -659,16 +652,16 @@ void *wm8750_dac_buffer(void *opaque, int samples)
     return ret;
 }
 
-void wm8750_dac_commit(void *opaque)
+static void wm8750_dac_commit(void *opaque)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
 
     wm8750_out_flush(s);
 }
 
-uint32_t wm8750_adc_dat(void *opaque)
+static uint32_t wm8750_adc_dat(void *opaque)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
     uint32_t *data;
 
     if (s->idx_in >= sizeof(s->data_in))
@@ -680,9 +673,9 @@ uint32_t wm8750_adc_dat(void *opaque)
     return *data;
 }
 
-void wm8750_set_bclk_in(void *opaque, int new_hz)
+static void wm8750_set_bclk_in(void *opaque, int new_hz)
 {
-    WM8750State *s = (WM8750State *) opaque;
+    WM8750State *s = WM8750(opaque);
 
     s->ext_adc_hz = new_hz;
     s->ext_dac_hz = new_hz;
@@ -693,6 +686,14 @@ static void wm8750_class_init(ObjectClass *klass, void 
*data)
 {
     DeviceClass *dc = DEVICE_CLASS(klass);
     I2CSlaveClass *sc = I2C_SLAVE_CLASS(klass);
+    AudioCodecClass *ac = AUDIO_CODEC_CLASS(klass);
+
+    ac->data_req_set = wm8750_data_req_set;
+    ac->dac_dat = wm8750_dac_dat;
+    ac->adc_dat = wm8750_adc_dat;
+    ac->dac_buffer = wm8750_dac_buffer;
+    ac->dac_commit = wm8750_dac_commit;
+    ac->set_bclk_in = wm8750_set_bclk_in;
 
     sc->init = wm8750_init;
     sc->event = wm8750_event;
@@ -702,8 +703,8 @@ static void wm8750_class_init(ObjectClass *klass, void 
*data)
 }
 
 static const TypeInfo wm8750_info = {
-    .name          = "wm8750",
-    .parent        = TYPE_I2C_SLAVE,
+    .name          = TYPE_WM8750,
+    .parent        = TYPE_AUDIO_CODEC,
     .instance_size = sizeof(WM8750State),
     .class_init    = wm8750_class_init,
 };
-- 
1.7.9.5


Reply via email to