1*1308e7f6Sjmcneill /* $NetBSD: dtv_ioctl.c,v 1.1 2011/07/09 14:46:56 jmcneill Exp $ */ 2*1308e7f6Sjmcneill 3*1308e7f6Sjmcneill /*- 4*1308e7f6Sjmcneill * Copyright (c) 2011 Jared D. McNeill <jmcneill@invisible.ca> 5*1308e7f6Sjmcneill * All rights reserved. 6*1308e7f6Sjmcneill * 7*1308e7f6Sjmcneill * Redistribution and use in source and binary forms, with or without 8*1308e7f6Sjmcneill * modification, are permitted provided that the following conditions 9*1308e7f6Sjmcneill * are met: 10*1308e7f6Sjmcneill * 1. Redistributions of source code must retain the above copyright 11*1308e7f6Sjmcneill * notice, this list of conditions and the following disclaimer. 12*1308e7f6Sjmcneill * 2. Redistributions in binary form must reproduce the above copyright 13*1308e7f6Sjmcneill * notice, this list of conditions and the following disclaimer in the 14*1308e7f6Sjmcneill * documentation and/or other materials provided with the distribution. 15*1308e7f6Sjmcneill * 3. All advertising materials mentioning features or use of this software 16*1308e7f6Sjmcneill * must display the following acknowledgement: 17*1308e7f6Sjmcneill * This product includes software developed by Jared D. McNeill. 18*1308e7f6Sjmcneill * 4. Neither the name of The NetBSD Foundation nor the names of its 19*1308e7f6Sjmcneill * contributors may be used to endorse or promote products derived 20*1308e7f6Sjmcneill * from this software without specific prior written permission. 21*1308e7f6Sjmcneill * 22*1308e7f6Sjmcneill * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 23*1308e7f6Sjmcneill * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 24*1308e7f6Sjmcneill * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 25*1308e7f6Sjmcneill * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 26*1308e7f6Sjmcneill * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 27*1308e7f6Sjmcneill * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 28*1308e7f6Sjmcneill * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 29*1308e7f6Sjmcneill * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 30*1308e7f6Sjmcneill * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 31*1308e7f6Sjmcneill * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 32*1308e7f6Sjmcneill * POSSIBILITY OF SUCH DAMAGE. 33*1308e7f6Sjmcneill */ 34*1308e7f6Sjmcneill 35*1308e7f6Sjmcneill #include <sys/cdefs.h> 36*1308e7f6Sjmcneill __KERNEL_RCSID(0, "$NetBSD: dtv_ioctl.c,v 1.1 2011/07/09 14:46:56 jmcneill Exp $"); 37*1308e7f6Sjmcneill 38*1308e7f6Sjmcneill #include <sys/param.h> 39*1308e7f6Sjmcneill #include <sys/types.h> 40*1308e7f6Sjmcneill #include <sys/conf.h> 41*1308e7f6Sjmcneill #include <sys/kmem.h> 42*1308e7f6Sjmcneill #include <sys/device.h> 43*1308e7f6Sjmcneill #include <sys/select.h> 44*1308e7f6Sjmcneill 45*1308e7f6Sjmcneill #include <dev/dtv/dtvvar.h> 46*1308e7f6Sjmcneill 47*1308e7f6Sjmcneill int 48*1308e7f6Sjmcneill dtv_frontend_ioctl(struct dtv_softc *sc, u_long cmd, void *data, int flags) 49*1308e7f6Sjmcneill { 50*1308e7f6Sjmcneill switch (cmd) { 51*1308e7f6Sjmcneill case FE_READ_STATUS: 52*1308e7f6Sjmcneill *(fe_status_t *)data = dtv_device_get_status(sc); 53*1308e7f6Sjmcneill return 0; 54*1308e7f6Sjmcneill case FE_READ_BER: 55*1308e7f6Sjmcneill *(uint32_t *)data = 0; /* XXX TODO */ 56*1308e7f6Sjmcneill return 0; 57*1308e7f6Sjmcneill case FE_READ_SNR: 58*1308e7f6Sjmcneill *(uint16_t *)data = dtv_device_get_snr(sc); 59*1308e7f6Sjmcneill return 0; 60*1308e7f6Sjmcneill case FE_READ_SIGNAL_STRENGTH: 61*1308e7f6Sjmcneill *(uint16_t *)data = dtv_device_get_signal_strength(sc); 62*1308e7f6Sjmcneill return 0; 63*1308e7f6Sjmcneill case FE_SET_FRONTEND: 64*1308e7f6Sjmcneill return dtv_device_set_tuner(sc, data); 65*1308e7f6Sjmcneill case FE_GET_INFO: 66*1308e7f6Sjmcneill dtv_device_get_devinfo(sc, data); 67*1308e7f6Sjmcneill return 0; 68*1308e7f6Sjmcneill default: 69*1308e7f6Sjmcneill return EINVAL; 70*1308e7f6Sjmcneill } 71*1308e7f6Sjmcneill } 72*1308e7f6Sjmcneill 73*1308e7f6Sjmcneill int 74*1308e7f6Sjmcneill dtv_demux_ioctl(struct dtv_softc *sc, u_long cmd, void *data, int flags) 75*1308e7f6Sjmcneill { 76*1308e7f6Sjmcneill struct dmx_pes_filter_params *pesfilt; 77*1308e7f6Sjmcneill uint16_t pid; 78*1308e7f6Sjmcneill size_t bufsize; 79*1308e7f6Sjmcneill int error; 80*1308e7f6Sjmcneill 81*1308e7f6Sjmcneill switch (cmd) { 82*1308e7f6Sjmcneill case DMX_START: 83*1308e7f6Sjmcneill if (sc->sc_bufsize_chg) { 84*1308e7f6Sjmcneill if ((error = dtv_buffer_setup(sc, sc->sc_bufsize)) != 0) 85*1308e7f6Sjmcneill return error; 86*1308e7f6Sjmcneill sc->sc_bufsize_chg = false; 87*1308e7f6Sjmcneill } 88*1308e7f6Sjmcneill return dtv_device_start_transfer(sc); 89*1308e7f6Sjmcneill case DMX_STOP: 90*1308e7f6Sjmcneill return dtv_device_stop_transfer(sc); 91*1308e7f6Sjmcneill case DMX_SET_BUFFER_SIZE: 92*1308e7f6Sjmcneill bufsize = *(uintptr_t *)data; 93*1308e7f6Sjmcneill if (bufsize >= DTV_DEFAULT_BUFSIZE && 94*1308e7f6Sjmcneill sc->sc_bufsize != bufsize) { 95*1308e7f6Sjmcneill sc->sc_bufsize = bufsize; 96*1308e7f6Sjmcneill sc->sc_bufsize_chg = true; 97*1308e7f6Sjmcneill } 98*1308e7f6Sjmcneill return 0; 99*1308e7f6Sjmcneill case DMX_SET_PES_FILTER: 100*1308e7f6Sjmcneill pesfilt = data; 101*1308e7f6Sjmcneill 102*1308e7f6Sjmcneill if (pesfilt->input != DMX_IN_FRONTEND) 103*1308e7f6Sjmcneill return EINVAL; 104*1308e7f6Sjmcneill if (pesfilt->output != DMX_OUT_TS_TAP) 105*1308e7f6Sjmcneill return EINVAL; 106*1308e7f6Sjmcneill if (pesfilt->pes_type != DMX_PES_OTHER) 107*1308e7f6Sjmcneill return EINVAL; 108*1308e7f6Sjmcneill 109*1308e7f6Sjmcneill error = dtv_demux_ioctl(sc, DMX_ADD_PID, &pesfilt->pid, flags); 110*1308e7f6Sjmcneill if (error) 111*1308e7f6Sjmcneill return error; 112*1308e7f6Sjmcneill 113*1308e7f6Sjmcneill if (pesfilt->flags & DMX_IMMEDIATE_START) { 114*1308e7f6Sjmcneill error = dtv_demux_ioctl(sc, DMX_START, NULL, flags); 115*1308e7f6Sjmcneill if (error) 116*1308e7f6Sjmcneill return error; 117*1308e7f6Sjmcneill } 118*1308e7f6Sjmcneill return 0; 119*1308e7f6Sjmcneill case DMX_ADD_PID: 120*1308e7f6Sjmcneill pid = *(uint16_t *)data; 121*1308e7f6Sjmcneill if (pid > 0x2000) 122*1308e7f6Sjmcneill return EINVAL; 123*1308e7f6Sjmcneill 124*1308e7f6Sjmcneill if (pid == 0x2000) { 125*1308e7f6Sjmcneill memset(sc->sc_ts.ts_pidfilter, 1, 126*1308e7f6Sjmcneill sizeof(sc->sc_ts.ts_pidfilter)); 127*1308e7f6Sjmcneill } else { 128*1308e7f6Sjmcneill sc->sc_ts.ts_pidfilter[pid] = 1; 129*1308e7f6Sjmcneill } 130*1308e7f6Sjmcneill return 0; 131*1308e7f6Sjmcneill case DMX_REMOVE_PID: 132*1308e7f6Sjmcneill pid = *(uint16_t *)data; 133*1308e7f6Sjmcneill if (pid > 0x2000) 134*1308e7f6Sjmcneill return EINVAL; 135*1308e7f6Sjmcneill 136*1308e7f6Sjmcneill if (pid == 0x2000) { 137*1308e7f6Sjmcneill memset(sc->sc_ts.ts_pidfilter, 0, 138*1308e7f6Sjmcneill sizeof(sc->sc_ts.ts_pidfilter)); 139*1308e7f6Sjmcneill } else { 140*1308e7f6Sjmcneill sc->sc_ts.ts_pidfilter[pid] = 0; 141*1308e7f6Sjmcneill } 142*1308e7f6Sjmcneill return 0; 143*1308e7f6Sjmcneill default: 144*1308e7f6Sjmcneill return EINVAL; 145*1308e7f6Sjmcneill } 146*1308e7f6Sjmcneill } 147