summaryrefslogtreecommitdiff
path: root/sys/dev/ic
diff options
context:
space:
mode:
authorGrigoriy Orlov <gluk@cvs.openbsd.org>2001-10-04 19:46:47 +0000
committerGrigoriy Orlov <gluk@cvs.openbsd.org>2001-10-04 19:46:47 +0000
commit4db40d19ace9e7a547e7307eb00024ba08ab1594 (patch)
treedf614c654107db62d008129257ca7afa988aad6c /sys/dev/ic
parentfe62460ed4e7176b7954fe6085d6b5d413e6867f (diff)
Chip specific parts for FM-radio drivers.
Work by Vladimir Popov <jumbo@narod.ru> and Maxim Tsyplakov <tm@oganer.net>
Diffstat (limited to 'sys/dev/ic')
-rw-r--r--sys/dev/ic/lm700x.c126
-rw-r--r--sys/dev/ic/lm700x.h79
-rw-r--r--sys/dev/ic/tea5757.c164
-rw-r--r--sys/dev/ic/tea5757.h88
4 files changed, 457 insertions, 0 deletions
diff --git a/sys/dev/ic/lm700x.c b/sys/dev/ic/lm700x.c
new file mode 100644
index 00000000000..45a09182f2a
--- /dev/null
+++ b/sys/dev/ic/lm700x.c
@@ -0,0 +1,126 @@
+/* $OpenBSD: lm700x.c,v 1.1 2001/10/04 19:46:46 gluk Exp $ */
+
+/*
+ * Copyright (c) 2001 Vladimir Popov <jumbo@narod.ru>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* Implementation of most common lm700x routines */
+
+#include <sys/param.h>
+#include <sys/radioio.h>
+
+#include <dev/ic/lm700x.h>
+
+u_long
+lm700x_encode_freq(u_long nfreq, u_long rf)
+{
+ u_char ref_freq;
+
+ switch (rf) {
+ case LM700X_REF_100:
+ ref_freq = 100;
+ break;
+ case LM700X_REF_025:
+ ref_freq = 25;
+ break;
+ case LM700X_REF_050:
+ /* FALLTHROUGH */
+ default:
+ ref_freq = 50;
+ break;
+ }
+
+ nfreq += IF_FREQ;
+ nfreq /= ref_freq;
+
+ return nfreq;
+}
+
+void
+lm700x_hardware_write(struct lm700x_t *lm, u_long data, u_long addon)
+{
+ int i;
+
+ lm->init(lm->iot, lm->ioh, lm->offset, lm->rsetdata | addon);
+
+ for (i = 0; i < LM700X_REGISTER_LENGTH; i++)
+ if (data & (1 << i)) {
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->wocl | addon);
+ DELAY(LM700X_WRITE_DELAY);
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->woch | addon);
+ DELAY(LM700X_WRITE_DELAY);
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->wocl | addon);
+ } else {
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->wzcl | addon);
+ DELAY(LM700X_WRITE_DELAY);
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->wzch | addon);
+ DELAY(LM700X_WRITE_DELAY);
+ bus_space_write_1(lm->iot, lm->ioh, lm->offset,
+ lm->wzcl | addon);
+ }
+
+ lm->rset(lm->iot, lm->ioh, lm->offset, lm->rsetdata | addon);
+}
+
+u_long
+lm700x_encode_ref(u_char rf)
+{
+ u_long ret;
+
+ if (rf < 36)
+ ret = LM700X_REF_025;
+ else if (rf > 35 && rf < 75)
+ ret = LM700X_REF_050;
+ else
+ ret = LM700X_REF_100;
+
+ return ret;
+}
+
+u_char
+lm700x_decode_ref(u_long rf)
+{
+ u_char ret;
+
+ switch (rf) {
+ case LM700X_REF_100:
+ ret = 100;
+ break;
+ case LM700X_REF_025:
+ ret = 25;
+ break;
+ case LM700X_REF_050:
+ /* FALLTHROUGH */
+ default:
+ ret = 50;
+ break;
+ }
+
+ return ret;
+}
diff --git a/sys/dev/ic/lm700x.h b/sys/dev/ic/lm700x.h
new file mode 100644
index 00000000000..4afab020242
--- /dev/null
+++ b/sys/dev/ic/lm700x.h
@@ -0,0 +1,79 @@
+/* $OpenBSD: lm700x.h,v 1.1 2001/10/04 19:46:46 gluk Exp $ */
+/* $RuOBSD: lm700x.h,v 1.3 2001/10/04 19:25:39 gluk Exp $ */
+
+/*
+ * Copyright (c) 2001 Vladimir Popov <jumbo@narod.ru>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef _LM700X_H_
+#define _LM700X_H_
+
+#include <sys/types.h>
+
+#include <machine/bus.h>
+
+#define LM700X_REGISTER_LENGTH 24
+
+#define LM700X_DATA_MASK 0xFFC000
+#define LM700X_FREQ_MASK 0x003FFF
+
+#define LM700X_FREQ(x) (x << 0) /* 0x003FFF */
+#define LM700X_LSI(x) (x << 14) /* 0x00C000 */ /* always zero */
+#define LM700X_BAND(x) (x << 16) /* 0x070000 */
+#define LM700X_STEREO LM700X_BAND(3)
+#define LM700X_MONO LM700X_BAND(1)
+#define LM700X_TIME_BASE(x) (x << 19) /* 0x080000 */ /* always zero */
+#define LM700X_REF_FREQ(x) (x << 20) /* 0x700000 */
+#define LM700X_REF_100 LM700X_REF_FREQ(0)
+#define LM700X_REF_025 LM700X_REF_FREQ(2)
+#define LM700X_REF_050 LM700X_REF_FREQ(4)
+/* The rest is for an AM band */
+
+#define LM700X_DIVIDER_AM (0 << 23) /* 0x000000 */
+#define LM700X_DIVIDER_FM (1 << 23) /* 0x800000 */
+
+#define LM700X_WRITE_DELAY 6 /* 6 microseconds */
+
+struct lm700x_t {
+ bus_space_tag_t iot;
+ bus_space_handle_t ioh;
+ bus_size_t offset;
+
+ u_long wzcl; /* write zero clock low */
+ u_long wzch; /* write zero clock high */
+ u_long wocl; /* write one clock low */
+ u_long woch; /* write one clock high */
+ u_long initdata;
+ u_long rsetdata;
+
+ void (*init)(bus_space_tag_t, bus_space_handle_t, bus_size_t, u_long);
+ void (*rset)(bus_space_tag_t, bus_space_handle_t, bus_size_t, u_long);
+};
+
+u_long lm700x_encode_freq(u_long, u_long);
+u_long lm700x_encode_ref(u_char);
+u_char lm700x_decode_ref(u_long);
+void lm700x_hardware_write(struct lm700x_t *, u_long, u_long);
+
+#endif /* _LM700X_H_ */
diff --git a/sys/dev/ic/tea5757.c b/sys/dev/ic/tea5757.c
new file mode 100644
index 00000000000..cb9aae00a0d
--- /dev/null
+++ b/sys/dev/ic/tea5757.c
@@ -0,0 +1,164 @@
+/* $OpenBSD: tea5757.c,v 1.1 2001/10/04 19:46:46 gluk Exp $ */
+
+/*
+ * Copyright (c) 2001 Vladimir Popov <jumbo@narod.ru>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* Implementation of most common TEA5757 routines */
+
+#include <sys/param.h>
+#include <sys/radioio.h>
+
+#include <dev/ic/tea5757.h>
+
+/*
+ * Convert frequency to hardware representation
+ */
+u_long
+tea5757_encode_freq(u_long freq)
+{
+#ifdef RADIO_TEA5759
+ freq -= IF_FREQ;
+#else
+ freq += IF_FREQ;
+#endif /* RADIO_TEA5759 */
+ /*
+ * NO FLOATING POINT!
+ */
+ freq *= 10;
+ freq /= 125;
+ return freq & TEA5757_FREQ;
+}
+
+/*
+ * Convert frequency from hardware representation
+ */
+u_long
+tea5757_decode_freq(u_long freq)
+{
+ freq &= TEA5757_FREQ;
+ freq *= 125; /* 12.5 kHz */
+ freq /= 10;
+#ifdef RADIO_TEA5759
+ freq += IF_FREQ;
+#else
+ freq -= IF_FREQ;
+#endif /* RADIO_TEA5759 */
+ return freq;
+}
+
+/*
+ * Hardware search
+ */
+void
+tea5757_search(struct tea5757_t *tea, u_long stereo, u_long lock, int dir)
+{
+ u_long reg;
+ u_int co = 0;
+
+ reg = stereo | lock | TEA5757_SEARCH_START;
+ reg |= dir ? TEA5757_SEARCH_UP : TEA5757_SEARCH_DOWN;
+ tea5757_hardware_write(tea, reg);
+
+ DELAY(TEA5757_ACQUISITION_DELAY);
+
+ do {
+ DELAY(TEA5757_WAIT_DELAY);
+ reg = tea->read(tea->iot, tea->ioh, tea->offset);
+ } while ((reg & TEA5757_FREQ) == 0 && ++co < 200);
+}
+
+void
+tea5757_hardware_write(struct tea5757_t *tea, u_long data)
+{
+ int i = TEA5757_REGISTER_LENGTH;
+
+ tea->init(tea->iot, tea->ioh, tea->offset, 0);
+
+ while (i--)
+ if (data & (1 << i))
+ tea->write_bit(tea->iot, tea->ioh, tea->offset, 1);
+ else
+ tea->write_bit(tea->iot, tea->ioh, tea->offset, 0);
+
+ tea->rset(tea->iot, tea->ioh, tea->offset, 0);
+}
+
+u_long
+tea5757_set_freq(struct tea5757_t *tea, u_long stereo, u_long lock, u_long freq)
+{
+ u_long data = 0ul;
+
+ if (freq < MIN_FM_FREQ)
+ freq = MIN_FM_FREQ;
+ if (freq > MAX_FM_FREQ)
+ freq = MAX_FM_FREQ;
+
+ data = tea5757_encode_freq(freq) | stereo | lock | TEA5757_SEARCH_END;
+ tea5757_hardware_write(tea, data);
+
+ return freq;
+}
+
+u_long
+tea5757_encode_lock(u_char lock)
+{
+ u_long ret;
+
+ if (lock < 8)
+ ret = TEA5757_S005;
+ else if (lock > 7 && lock < 15)
+ ret = TEA5757_S010;
+ else if (lock > 14 && lock < 51)
+ ret = TEA5757_S030;
+ else if (lock > 50)
+ ret = TEA5757_S150;
+
+ return ret;
+}
+
+u_char
+tea5757_decode_lock(u_long lock)
+{
+ u_char ret;
+
+ switch (lock) {
+ case TEA5757_S005:
+ ret = 5;
+ break;
+ case TEA5757_S010:
+ ret = 10;
+ break;
+ case TEA5757_S030:
+ ret = 30;
+ break;
+ case TEA5757_S150:
+ /* FALLTHROUGH */
+ default:
+ ret = 150;
+ break;
+ }
+
+ return ret;
+}
diff --git a/sys/dev/ic/tea5757.h b/sys/dev/ic/tea5757.h
new file mode 100644
index 00000000000..a9aca55dcf2
--- /dev/null
+++ b/sys/dev/ic/tea5757.h
@@ -0,0 +1,88 @@
+/* $OpenBSD: tea5757.h,v 1.1 2001/10/04 19:46:46 gluk Exp $ */
+/* $RuOBSD: tea5757.h,v 1.5 2001/10/04 18:51:50 pva Exp $ */
+
+/*
+ * Copyright (c) 2001 Vladimir Popov <jumbo@narod.ru>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef _TEA5757_H_
+#define _TEA5757_H_
+
+#include <sys/types.h>
+
+#include <machine/bus.h>
+
+#define TEA5757_REGISTER_LENGTH 25
+#define TEA5757_FREQ 0x0007FFF
+#define TEA5757_DATA 0x1FF8000
+
+#define TEA5757_SEARCH_START (1 << 24) /* 0x1000000 */
+#define TEA5757_SEARCH_END (0 << 24) /* 0x0000000 */
+
+#define TEA5757_SEARCH_UP (1 << 23) /* 0x0800000 */
+#define TEA5757_SEARCH_DOWN (0 << 23) /* 0x0000000 */
+#define TEA5757_ACQUISITION_DELAY 100000
+#define TEA5757_WAIT_DELAY 1000
+#define TEA5757_SEARCH_DELAY 14 /* 14 microseconds */
+
+#define TEA5757_STEREO (0 << 22) /* 0x0000000 */
+#define TEA5757_MONO (1 << 22) /* 0x0400000 */
+
+#define TEA5757_BAND_FM (0 << 20)
+#define TEA5757_BAND_MW (1 << 20)
+#define TEA5757_BAND_LW (2 << 20)
+#define TEA5757_BAND_SW (3 << 20)
+
+#define TEA5757_USER_PORT (0 << 18)
+#define TEA5757_DUMMY (0 << 15)
+
+#define TEA5757_S005 (0 << 16) /* 0x0000000 * > 5 mkV */
+#define TEA5757_S010 (2 << 16) /* 0x0020000 * > 10 mkV */
+#define TEA5757_S030 (1 << 16) /* 0x0010000 * > 30 mkV */
+#define TEA5757_S150 (3 << 16) /* 0x0030000 * > 150 mkV */
+
+struct tea5757_t {
+ bus_space_tag_t iot;
+ bus_space_handle_t ioh;
+ bus_size_t offset;
+
+ void (*init)(bus_space_tag_t, bus_space_handle_t, bus_size_t,
+ u_long); /* init value */
+ void (*rset)(bus_space_tag_t, bus_space_handle_t, bus_size_t,
+ u_long); /* reset value */
+ void (*write_bit)(bus_space_tag_t, bus_space_handle_t, bus_size_t,
+ u_char); /* the bit */
+ u_long (*read)(bus_space_tag_t, bus_space_handle_t, bus_size_t);
+};
+
+u_long tea5757_encode_freq(u_long);
+u_long tea5757_decode_freq(u_long);
+u_long tea5757_encode_lock(u_char);
+u_char tea5757_decode_lock(u_long);
+
+u_long tea5757_set_freq(struct tea5757_t *, u_long, u_long, u_long);
+void tea5757_search(struct tea5757_t *, u_long, u_long, int);
+
+void tea5757_hardware_write(struct tea5757_t *, u_long);
+
+#endif /* _TEA5757_H_ */