]> rtime.felk.cvut.cz Git - sojka/nv-tegra/linux-3.10.git/commitdiff
staging: comedi: pcl818: remove unused RTC dma support
authorH Hartley Sweeten <hsweeten@visionengravers.com>
Sat, 20 Apr 2013 00:14:06 +0000 (17:14 -0700)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 22 Apr 2013 17:23:37 +0000 (10:23 -0700)
All the RTC dma support code in this driver is #ifdef'ed out.

Remove the unused code to assist in cleaning up this driver.

Signed-off-by: H Hartley Sweeten <hsweeten@visionengravers.com>
Cc: Ian Abbott <abbotti@mev.co.uk>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
drivers/staging/comedi/drivers/pcl818.c

index 142449d7f8b474316f928d42c72fc516e27c521c..91cb1bd6717fd986d111d6684b4aa315aa3a299d 100644 (file)
@@ -98,15 +98,15 @@ A word or two about DMA. Driver support DMA operations at two ways:
 
 */
 
-#include "../comedidev.h"
-
 #include <linux/ioport.h>
-#include <linux/mc146818rtc.h>
 #include <linux/gfp.h>
 #include <linux/delay.h>
 #include <linux/io.h>
+#include <linux/interrupt.h>
 #include <asm/dma.h>
 
+#include "../comedidev.h"
+
 #include "comedi_fc.h"
 #include "8253.h"
 
@@ -186,15 +186,6 @@ A word or two about DMA. Driver support DMA operations at two ways:
 #define INT_TYPE_AO3_INT 8
 #endif
 
-#ifdef unused
-/* RTC stuff... */
-#define INT_TYPE_AI1_DMA_RTC 9
-#define INT_TYPE_AI3_DMA_RTC 10
-
-#define RTC_IRQ        8
-#define RTC_IO_EXTENT  0x10
-#endif
-
 #define MAGIC_DMA_WORD 0x5a5a
 
 static const struct comedi_lrange range_pcl818h_ai = { 9, {
@@ -248,11 +239,6 @@ static const struct comedi_lrange range718_bipolar0_5 = {
 static const struct comedi_lrange range718_unipolar2 = { 1, {UNI_RANGE(2),} };
 static const struct comedi_lrange range718_unipolar1 = { 1, {BIP_RANGE(1),} };
 
-#ifdef unused
-static int RTC_lock;   /* RTC lock */
-static int RTC_timer_lock;     /* RTC int lock */
-#endif
-
 struct pcl818_board {
 
        const char *name;       /*  driver name */
@@ -277,22 +263,11 @@ struct pcl818_board {
 struct pcl818_private {
 
        unsigned int dma;       /*  used DMA, 0=don't use DMA */
-       int dma_rtc;            /*  1=RTC used with DMA, 0=no RTC alloc */
        unsigned int io_range;
-#ifdef unused
-       unsigned long rtc_iobase;       /*  RTC port region */
-       unsigned int rtc_iosize;
-       unsigned int rtc_irq;
-       struct timer_list rtc_irq_timer;        /*  timer for RTC sanity check */
-       unsigned long rtc_freq; /*  RTC int freq */
-       int rtc_irq_blocked;    /*  1=we now do AI with DMA&RTC */
-#endif
        unsigned long dmabuf[2];        /*  pointers to begin of DMA buffers */
        unsigned int dmapages[2];       /*  len of DMA buffers in PAGE_SIZEs */
        unsigned int hwdmaptr[2];       /*  hardware address of DMA buffers */
        unsigned int hwdmasize[2];      /*  len of DMA buffers in Bytes */
-       unsigned int dmasamplsize;      /*  size in samples hwdmasize[0]/2 */
-       unsigned int last_top_dma;      /*  DMA pointer in last RTC int */
        int next_dma_buf;       /*  which DMA buffer will be used next round */
        long dma_runs_to_end;   /*  how many we must permorm DMA transfer to end of record */
        unsigned long last_dma_run;     /*  how many bytes we must transfer on last DMA page */
@@ -342,12 +317,6 @@ static int pcl818_ai_cancel(struct comedi_device *dev,
 static void start_pacer(struct comedi_device *dev, int mode,
                        unsigned int divisor1, unsigned int divisor2);
 
-#ifdef unused
-static int set_rtc_irq_bit(unsigned char bit);
-static void rtc_dropped_irq(unsigned long data);
-static int rtc_setfreq_irq(int freq);
-#endif
-
 /*
 ==============================================================================
    ANALOG INPUT MODE0, 818 cards, slow version
@@ -610,113 +579,6 @@ static irqreturn_t interrupt_pcl818_ai_mode13_dma(int irq, void *d)
        return IRQ_HANDLED;
 }
 
-#ifdef unused
-/*
-==============================================================================
-   analog input dma mode 1 & 3 over RTC, 818 cards
-*/
-static irqreturn_t interrupt_pcl818_ai_mode13_dma_rtc(int irq, void *d)
-{
-       struct comedi_device *dev = d;
-       struct pcl818_private *devpriv = dev->private;
-       struct comedi_subdevice *s = &dev->subdevices[0];
-       unsigned long tmp;
-       unsigned int top1, top2, i, bufptr;
-       long ofs_dats;
-       short *dmabuf = (short *)devpriv->dmabuf[0];
-
-       /* outb(2,0x378); */
-       switch (devpriv->ai_mode) {
-       case INT_TYPE_AI1_DMA_RTC:
-       case INT_TYPE_AI3_DMA_RTC:
-               tmp = (CMOS_READ(RTC_INTR_FLAGS) & 0xF0);
-               mod_timer(&devpriv->rtc_irq_timer,
-                         jiffies + HZ / devpriv->rtc_freq + 2 * HZ / 100);
-
-               for (i = 0; i < 10; i++) {
-                       top1 = get_dma_residue(devpriv->dma);
-                       top2 = get_dma_residue(devpriv->dma);
-                       if (top1 == top2)
-                               break;
-               }
-
-               if (top1 != top2)
-                       return IRQ_HANDLED;
-               top1 = devpriv->hwdmasize[0] - top1;    /*  where is now DMA in buffer */
-               top1 >>= 1;
-               ofs_dats = top1 - devpriv->last_top_dma;        /*  new samples from last call */
-               if (ofs_dats < 0)
-                       ofs_dats = (devpriv->dmasamplsize) + ofs_dats;
-               if (!ofs_dats)
-                       return IRQ_HANDLED;     /*  exit=no new samples from last call */
-               /*  obsluz data */
-               i = devpriv->last_top_dma - 1;
-               i &= (devpriv->dmasamplsize - 1);
-
-               if (dmabuf[i] != MAGIC_DMA_WORD) {      /*  DMA overflow! */
-                       comedi_error(dev, "A/D mode1/3 DMA buffer overflow!");
-                       /* printk("I %d dmabuf[i] %d %d\n",i,dmabuf[i],devpriv->dmasamplsize); */
-                       pcl818_ai_cancel(dev, s);
-                       s->async->events |= COMEDI_CB_EOA | COMEDI_CB_ERROR;
-                       comedi_event(dev, s);
-                       return IRQ_HANDLED;
-               }
-               /* printk("r %ld ",ofs_dats); */
-
-               bufptr = devpriv->last_top_dma;
-
-               for (i = 0; i < ofs_dats; i++) {
-                       if ((dmabuf[bufptr] & 0xf) != devpriv->act_chanlist[devpriv->act_chanlist_pos]) {       /*  dropout! */
-                               printk
-                                   ("comedi: A/D mode1/3 DMA - channel dropout %d!=%d !\n",
-                                    (dmabuf[bufptr] & 0xf),
-                                    devpriv->
-                                    act_chanlist[devpriv->act_chanlist_pos]);
-                               pcl818_ai_cancel(dev, s);
-                               s->async->events |=
-                                   COMEDI_CB_EOA | COMEDI_CB_ERROR;
-                               comedi_event(dev, s);
-                               return IRQ_HANDLED;
-                       }
-
-                       comedi_buf_put(s->async, dmabuf[bufptr++] >> 4);        /*  get one sample */
-                       bufptr &= (devpriv->dmasamplsize - 1);
-
-                       devpriv->act_chanlist_pos++;
-                       if (devpriv->act_chanlist_pos >=
-                                       devpriv->act_chanlist_len) {
-                               devpriv->act_chanlist_pos = 0;
-                       }
-                       s->async->cur_chan++;
-                       if (s->async->cur_chan >= devpriv->ai_n_chan) {
-                               s->async->cur_chan = 0;
-                               devpriv->ai_act_scan--;
-                       }
-
-                       if (!devpriv->neverending_ai)
-                               if (devpriv->ai_act_scan == 0) {        /* all data sampled */
-                                       pcl818_ai_cancel(dev, s);
-                                       s->async->events |= COMEDI_CB_EOA;
-                                       comedi_event(dev, s);
-                                       /* printk("done int ai13 dma\n"); */
-                                       return IRQ_HANDLED;
-                               }
-               }
-
-               devpriv->last_top_dma = bufptr;
-               bufptr--;
-               bufptr &= (devpriv->dmasamplsize - 1);
-               dmabuf[bufptr] = MAGIC_DMA_WORD;
-               comedi_event(dev, s);
-               /* outb(0,0x378); */
-               return IRQ_HANDLED;
-       }
-
-       /* outb(0,0x378); */
-       return IRQ_HANDLED;
-}
-#endif
-
 /*
 ==============================================================================
    analog input interrupt mode 1 & 3, 818HD/HG cards
@@ -900,49 +762,6 @@ static void pcl818_ai_mode13dma_int(int mode, struct comedi_device *dev,
        };
 }
 
-#ifdef unused
-/*
-==============================================================================
-   ANALOG INPUT MODE 1 or 3 DMA rtc, 818 cards
-*/
-static void pcl818_ai_mode13dma_rtc(int mode, struct comedi_device *dev,
-                                   struct comedi_subdevice *s)
-{
-       struct pcl818_private *devpriv = dev->private;
-       unsigned int flags;
-       short *pole;
-
-       set_dma_mode(devpriv->dma, DMA_MODE_READ | DMA_AUTOINIT);
-       flags = claim_dma_lock();
-       clear_dma_ff(devpriv->dma);
-       set_dma_addr(devpriv->dma, devpriv->hwdmaptr[0]);
-       set_dma_count(devpriv->dma, devpriv->hwdmasize[0]);
-       release_dma_lock(flags);
-       enable_dma(devpriv->dma);
-       devpriv->last_top_dma = 0;      /* devpriv->hwdmasize[0]; */
-       pole = (short *)devpriv->dmabuf[0];
-       devpriv->dmasamplsize = devpriv->hwdmasize[0] / 2;
-       pole[devpriv->dmasamplsize - 1] = MAGIC_DMA_WORD;
-#ifdef unused
-       devpriv->rtc_freq = rtc_setfreq_irq(2048);
-       devpriv->rtc_irq_timer.expires =
-           jiffies + HZ / devpriv->rtc_freq + 2 * HZ / 100;
-       devpriv->rtc_irq_timer.data = (unsigned long)dev;
-       devpriv->rtc_irq_timer.function = rtc_dropped_irq;
-
-       add_timer(&devpriv->rtc_irq_timer);
-#endif
-
-       if (mode == 1) {
-               devpriv->int818_mode = INT_TYPE_AI1_DMA_RTC;
-               outb(0x07 | (dev->irq << 4), dev->iobase + PCL818_CONTROL);     /* Pacer+DMA */
-       } else {
-               devpriv->int818_mode = INT_TYPE_AI3_DMA_RTC;
-               outb(0x06 | (dev->irq << 4), dev->iobase + PCL818_CONTROL);     /* Ext trig+DMA */
-       };
-}
-#endif
-
 /*
 ==============================================================================
    ANALOG INPUT MODE 1 or 3, 818 cards
@@ -956,7 +775,7 @@ static int pcl818_ai_cmd_mode(int mode, struct comedi_device *dev,
        unsigned int seglen;
 
        dev_dbg(dev->class_dev, "pcl818_ai_cmd_mode()\n");
-       if ((!dev->irq) && (!devpriv->dma_rtc)) {
+       if (!dev->irq) {
                comedi_error(dev, "IRQ not defined!");
                return -EINVAL;
        }
@@ -1005,15 +824,7 @@ static int pcl818_ai_cmd_mode(int mode, struct comedi_device *dev,
        switch (devpriv->dma) {
        case 1:         /*  DMA */
        case 3:
-               if (devpriv->dma_rtc == 0)
-                       pcl818_ai_mode13dma_int(mode, dev, s);
-#ifdef unused
-               else
-                       pcl818_ai_mode13dma_rtc(mode, dev, s);
-#else
-               else
-                       return -EINVAL;
-#endif
+               pcl818_ai_mode13dma_int(mode, dev, s);
                break;
        case 0:
                if (!devpriv->usefifo) {
@@ -1047,97 +858,10 @@ static int pcl818_ai_cmd_mode(int mode, struct comedi_device *dev,
 
        start_pacer(dev, mode, divisor1, divisor2);
 
-#ifdef unused
-       switch (devpriv->ai_mode) {
-       case INT_TYPE_AI1_DMA_RTC:
-       case INT_TYPE_AI3_DMA_RTC:
-               set_rtc_irq_bit(1);     /* start RTC */
-               break;
-       }
-#endif
        dev_dbg(dev->class_dev, "pcl818_ai_cmd_mode() end\n");
        return 0;
 }
 
-#ifdef unused
-/*
-==============================================================================
-   ANALOG OUTPUT MODE 1 or 3, 818 cards
-*/
-#ifdef PCL818_MODE13_AO
-static int pcl818_ao_mode13(int mode, struct comedi_device *dev,
-                           struct comedi_subdevice *s, comedi_trig *it)
-{
-       struct pcl818_private *devpriv = dev->private;
-       int divisor1 = 0, divisor2 = 0;
-
-       if (!dev->irq) {
-               comedi_error(dev, "IRQ not defined!");
-               return -EINVAL;
-       }
-
-       if (devpriv->irq_blocked)
-               return -EBUSY;
-
-       start_pacer(dev, -1, 0, 0);     /*  stop pacer */
-
-       devpriv->int13_act_scan = it->n;
-       devpriv->int13_act_chan = 0;
-       devpriv->irq_blocked = 1;
-       devpriv->irq_was_now_closed = 0;
-       devpriv->neverending_ai = 0;
-       devpriv->act_chanlist_pos = 0;
-
-       if (mode == 1) {
-               i8253_cascade_ns_to_timer(devpriv->i8253_osc_base, &divisor1,
-                                         &divisor2, &it->trigvar,
-                                         TRIG_ROUND_NEAREST);
-               if (divisor1 == 1) {    /* PCL818 crash if any divisor is set to 1 */
-                       divisor1 = 2;
-                       divisor2 /= 2;
-               }
-               if (divisor2 == 1) {
-                       divisor2 = 2;
-                       divisor1 /= 2;
-               }
-       }
-
-       outb(0, dev->iobase + PCL818_CNTENABLE);        /* enable pacer */
-       if (mode == 1) {
-               devpriv->int818_mode = INT_TYPE_AO1_INT;
-               outb(0x83 | (dev->irq << 4), dev->iobase + PCL818_CONTROL);     /* Pacer+IRQ */
-       } else {
-               devpriv->int818_mode = INT_TYPE_AO3_INT;
-               outb(0x82 | (dev->irq << 4), dev->iobase + PCL818_CONTROL);     /* Ext trig+IRQ */
-       };
-
-       start_pacer(dev, mode, divisor1, divisor2);
-
-       return 0;
-}
-
-/*
-==============================================================================
-   ANALOG OUTPUT MODE 1, 818 cards
-*/
-static int pcl818_ao_mode1(struct comedi_device *dev,
-                          struct comedi_subdevice *s, comedi_trig *it)
-{
-       return pcl818_ao_mode13(1, dev, s, it);
-}
-
-/*
-==============================================================================
-   ANALOG OUTPUT MODE 3, 818 cards
-*/
-static int pcl818_ao_mode3(struct comedi_device *dev,
-                          struct comedi_subdevice *s, comedi_trig *it)
-{
-       return pcl818_ao_mode13(3, dev, s, it);
-}
-#endif
-#endif
-
 /*
 ==============================================================================
  Start/stop pacer onboard pacer
@@ -1391,12 +1115,6 @@ static int pcl818_ai_cancel(struct comedi_device *dev,
                devpriv->irq_was_now_closed = 1;
 
                switch (devpriv->ai_mode) {
-#ifdef unused
-               case INT_TYPE_AI1_DMA_RTC:
-               case INT_TYPE_AI3_DMA_RTC:
-                       set_rtc_irq_bit(0);     /*  stop RTC */
-                       del_timer(&devpriv->rtc_irq_timer);
-#endif
                case INT_TYPE_AI1_DMA:
                case INT_TYPE_AI3_DMA:
                        if (devpriv->neverending_ai ||
@@ -1499,96 +1217,6 @@ static void pcl818_reset(struct comedi_device *dev)
        }
 }
 
-#ifdef unused
-/*
-==============================================================================
-  Enable(1)/disable(0) periodic interrupts from RTC
-*/
-static int set_rtc_irq_bit(unsigned char bit)
-{
-       unsigned char val;
-       unsigned long flags;
-
-       if (bit == 1) {
-               RTC_timer_lock++;
-               if (RTC_timer_lock > 1)
-                       return 0;
-       } else {
-               RTC_timer_lock--;
-               if (RTC_timer_lock < 0)
-                       RTC_timer_lock = 0;
-               if (RTC_timer_lock > 0)
-                       return 0;
-       }
-
-       save_flags(flags);
-       cli();
-       val = CMOS_READ(RTC_CONTROL);
-       if (bit)
-               val |= RTC_PIE;
-       else
-               val &= ~RTC_PIE;
-
-       CMOS_WRITE(val, RTC_CONTROL);
-       CMOS_READ(RTC_INTR_FLAGS);
-       restore_flags(flags);
-       return 0;
-}
-
-/*
-==============================================================================
-  Restart RTC if something stop it (xntpd every 11 mins or large IDE transfers)
-*/
-static void rtc_dropped_irq(unsigned long data)
-{
-       struct comedi_device *dev = (void *)data;
-       struct pcl818_private *devpriv = dev->private;
-       unsigned long flags, tmp;
-
-       switch (devpriv->int818_mode) {
-       case INT_TYPE_AI1_DMA_RTC:
-       case INT_TYPE_AI3_DMA_RTC:
-               mod_timer(&devpriv->rtc_irq_timer,
-                         jiffies + HZ / devpriv->rtc_freq + 2 * HZ / 100);
-               save_flags(flags);
-               cli();
-               tmp = (CMOS_READ(RTC_INTR_FLAGS) & 0xF0);       /* restart */
-               restore_flags(flags);
-               break;
-       }
-}
-
-/*
-==============================================================================
-  Set frequency of interrupts from RTC
-*/
-static int rtc_setfreq_irq(int freq)
-{
-       int tmp = 0;
-       int rtc_freq;
-       unsigned char val;
-       unsigned long flags;
-
-       if (freq < 2)
-               freq = 2;
-       if (freq > 8192)
-               freq = 8192;
-
-       while (freq > (1 << tmp))
-               tmp++;
-
-       rtc_freq = 1 << tmp;
-
-       save_flags(flags);
-       cli();
-       val = CMOS_READ(RTC_FREQ_SELECT) & 0xf0;
-       val |= (16 - tmp);
-       CMOS_WRITE(val, RTC_FREQ_SELECT);
-       restore_flags(flags);
-       return rtc_freq;
-}
-#endif
-
 static int pcl818_attach(struct comedi_device *dev, struct comedi_devconfig *it)
 {
        const struct pcl818_board *board = comedi_board(dev);
@@ -1652,42 +1280,10 @@ static int pcl818_attach(struct comedi_device *dev, struct comedi_devconfig *it)
        devpriv->irq_blocked = 0;       /* number of subdevice which use IRQ */
        devpriv->ai_mode = 0;   /* mode of irq */
 
-#ifdef unused
-       /* grab RTC for DMA operations */
-       devpriv->dma_rtc = 0;
-       if (it->options[2] > 0) {       /*  we want to use DMA */
-               if (RTC_lock == 0) {
-                       ret = __comedi_request_resource(dev, RTC_PORT(0),
-                                                       RTC_IO_EXTENT);
-                       if (ret)
-                               goto no_rtc;
-               }
-               devpriv->rtc_iobase = RTC_PORT(0);
-               devpriv->rtc_iosize = RTC_IO_EXTENT;
-               RTC_lock++;
-               if (!request_irq(RTC_IRQ, interrupt_pcl818_ai_mode13_dma_rtc, 0,
-                                "pcl818 DMA (RTC)", dev)) {
-                       devpriv->dma_rtc = 1;
-                       devpriv->rtc_irq = RTC_IRQ;
-                       printk(KERN_DEBUG "dma_irq=%u", devpriv->rtc_irq);
-               } else {
-                       RTC_lock--;
-                       if (RTC_lock == 0) {
-                               if (devpriv->rtc_iobase)
-                                       release_region(devpriv->rtc_iobase,
-                                                      devpriv->rtc_iosize);
-                       }
-                       devpriv->rtc_iobase = 0;
-                       devpriv->rtc_iosize = 0;
-               }
-       }
-
-no_rtc:
-#endif
        /* grab our DMA */
        dma = 0;
        devpriv->dma = dma;
-       if ((devpriv->irq_free == 0) && (devpriv->dma_rtc == 0))
+       if (!devpriv->irq_free)
                goto no_dma;    /* if we haven't IRQ, we can't use DMA */
        if (board->DMAbits != 0) {      /* board support DMA */
                dma = it->options[2];
@@ -1710,15 +1306,12 @@ no_rtc:
                devpriv->hwdmaptr[0] = virt_to_bus((void *)devpriv->dmabuf[0]);
                devpriv->hwdmasize[0] = (1 << pages) * PAGE_SIZE;
                /* printk("%d %d %ld, ",devpriv->dmapages[0],devpriv->hwdmasize[0],PAGE_SIZE); */
-               if (devpriv->dma_rtc == 0) {    /*  we must do duble buff :-( */
-                       devpriv->dmabuf[1] = __get_dma_pages(GFP_KERNEL, pages);
-                       if (!devpriv->dmabuf[1])
-                               return -EBUSY;
-                       devpriv->dmapages[1] = pages;
-                       devpriv->hwdmaptr[1] =
-                           virt_to_bus((void *)devpriv->dmabuf[1]);
-                       devpriv->hwdmasize[1] = (1 << pages) * PAGE_SIZE;
-               }
+               devpriv->dmabuf[1] = __get_dma_pages(GFP_KERNEL, pages);
+               if (!devpriv->dmabuf[1])
+                       return -EBUSY;
+               devpriv->dmapages[1] = pages;
+               devpriv->hwdmaptr[1] = virt_to_bus((void *)devpriv->dmabuf[1]);
+               devpriv->hwdmasize[1] = (1 << pages) * PAGE_SIZE;
        }
 
 no_dma:
@@ -1748,7 +1341,7 @@ no_dma:
                s->range_table = board->ai_range_type;
                s->cancel = pcl818_ai_cancel;
                s->insn_read = pcl818_ai_insn_read;
-               if ((irq) || (devpriv->dma_rtc)) {
+               if (irq) {
                        dev->read_subdev = s;
                        s->subdev_flags |= SDF_CMD_READ;
                        s->do_cmdtest = ai_cmdtest;
@@ -1805,14 +1398,6 @@ no_dma:
                s->range_table = board->ao_range_type;
                s->insn_read = pcl818_ao_insn_read;
                s->insn_write = pcl818_ao_insn_write;
-#ifdef unused
-#ifdef PCL818_MODE13_AO
-               if (irq) {
-                       s->trig[1] = pcl818_ao_mode1;
-                       s->trig[3] = pcl818_ao_mode3;
-               }
-#endif
-#endif
                if (board->is_818) {
                        if ((it->options[4] == 1) || (it->options[4] == 10))
                                s->range_table = &range_unipolar10;
@@ -1886,17 +1471,6 @@ static void pcl818_detach(struct comedi_device *dev)
                        free_pages(devpriv->dmabuf[0], devpriv->dmapages[0]);
                if (devpriv->dmabuf[1])
                        free_pages(devpriv->dmabuf[1], devpriv->dmapages[1]);
-#ifdef unused
-               if (devpriv->rtc_irq)
-                       free_irq(devpriv->rtc_irq, dev);
-               if ((devpriv->dma_rtc) && (RTC_lock == 1)) {
-                       if (devpriv->rtc_iobase)
-                               release_region(devpriv->rtc_iobase,
-                                              devpriv->rtc_iosize);
-               }
-               if (devpriv->dma_rtc)
-                       RTC_lock--;
-#endif
        }
        comedi_legacy_detach(dev);
 }