~ubuntu-branches/ubuntu/raring/virtualbox-ose/raring

« back to all changes in this revision

Viewing changes to src/VBox/Devices/Serial/DevSerial.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Felix Geyer
  • Date: 2009-12-18 16:44:29 UTC
  • mfrom: (0.3.3 upstream) (0.4.6 squeeze)
  • Revision ID: james.westby@ubuntu.com-20091218164429-jd34ccexpv5na11a
Tags: 3.1.2-dfsg-1ubuntu1
* Merge from Debian unstable (LP: #498219), remaining changes:
  - Disable update action
    - debian/patches/u01-disable-update-action.dpatch
  - VirtualBox should go in Accessories, not in System tools (LP: #288590)
    - debian/virtualbox-ose-qt.files/virtualbox-ose.desktop
  - Add Apport hook
    - debian/virtualbox-ose.files/source_virtualbox-ose.py
    - debian/virtualbox-ose.install
  - Add Launchpad integration
    - debian/control
    - debian/lpi-bug.xpm
    - debian/patches/u02-lp-integration.dpatch
* Fixes the following bugs:
  - Kernel module fails to build with Linux >= 2.6.32 (LP: #474625)
  - X.Org drivers need to be rebuilt against X-Server 1.7 (LP: #495935)
  - The *-source packages try to build the kernel modules even though the
    kernel headers aren't available (LP: #473334)
* Replace *-source packages with transitional packages for *-dkms.
* Adapt u01-disable-update-action.dpatch and u02-lp-integration.dpatch for
  new upstream version.

Show diffs side-by-side

added added

removed removed

Lines of Context:
71
71
*******************************************************************************/
72
72
#define SERIAL_SAVED_STATE_VERSION  3
73
73
 
74
 
#define UART_LCR_DLAB               0x80        /* Divisor latch access bit */
75
 
 
76
 
#define UART_IER_MSI                0x08        /* Enable Modem status interrupt */
77
 
#define UART_IER_RLSI               0x04        /* Enable receiver line status interrupt */
78
 
#define UART_IER_THRI               0x02        /* Enable Transmitter holding register int. */
79
 
#define UART_IER_RDI                0x01        /* Enable receiver data interrupt */
80
 
 
81
 
#define UART_IIR_NO_INT             0x01        /* No interrupts pending */
82
 
#define UART_IIR_ID                     0x06    /* Mask for the interrupt ID */
83
 
 
84
 
#define UART_IIR_MSI                0x00        /* Modem status interrupt */
85
 
#define UART_IIR_THRI               0x02        /* Transmitter holding register empty */
86
 
#define UART_IIR_RDI                0x04        /* Receiver data interrupt */
87
 
#define UART_IIR_RLSI               0x06        /* Receiver line status interrupt */
 
74
#define UART_LCR_DLAB               0x80        /* Divisor latch access bit */
 
75
 
 
76
#define UART_IER_MSI                0x08        /* Enable Modem status interrupt */
 
77
#define UART_IER_RLSI               0x04        /* Enable receiver line status interrupt */
 
78
#define UART_IER_THRI               0x02        /* Enable Transmitter holding register int. */
 
79
#define UART_IER_RDI                0x01        /* Enable receiver data interrupt */
 
80
 
 
81
#define UART_IIR_NO_INT             0x01        /* No interrupts pending */
 
82
#define UART_IIR_ID                     0x06    /* Mask for the interrupt ID */
 
83
 
 
84
#define UART_IIR_MSI                0x00        /* Modem status interrupt */
 
85
#define UART_IIR_THRI               0x02        /* Transmitter holding register empty */
 
86
#define UART_IIR_RDI                0x04        /* Receiver data interrupt */
 
87
#define UART_IIR_RLSI               0x06        /* Receiver line status interrupt */
88
88
 
89
89
/*
90
90
 * These are the definitions for the Modem Control Register
91
91
 */
92
 
#define UART_MCR_LOOP               0x10        /* Enable loopback test mode */
93
 
#define UART_MCR_OUT2               0x08        /* Out2 complement */
94
 
#define UART_MCR_OUT1               0x04        /* Out1 complement */
95
 
#define UART_MCR_RTS                0x02        /* RTS complement */
96
 
#define UART_MCR_DTR                0x01        /* DTR complement */
 
92
#define UART_MCR_LOOP               0x10        /* Enable loopback test mode */
 
93
#define UART_MCR_OUT2               0x08        /* Out2 complement */
 
94
#define UART_MCR_OUT1               0x04        /* Out1 complement */
 
95
#define UART_MCR_RTS                0x02        /* RTS complement */
 
96
#define UART_MCR_DTR                0x01        /* DTR complement */
97
97
 
98
98
/*
99
99
 * These are the definitions for the Modem Status Register
100
100
 */
101
 
#define UART_MSR_DCD                0x80        /* Data Carrier Detect */
102
 
#define UART_MSR_RI                     0x40    /* Ring Indicator */
103
 
#define UART_MSR_DSR                0x20        /* Data Set Ready */
104
 
#define UART_MSR_CTS                0x10        /* Clear to Send */
105
 
#define UART_MSR_DDCD               0x08        /* Delta DCD */
106
 
#define UART_MSR_TERI               0x04        /* Trailing edge ring indicator */
107
 
#define UART_MSR_DDSR               0x02        /* Delta DSR */
108
 
#define UART_MSR_DCTS               0x01        /* Delta CTS */
109
 
#define UART_MSR_ANY_DELTA          0x0F        /* Any of the delta bits! */
 
101
#define UART_MSR_DCD                0x80        /* Data Carrier Detect */
 
102
#define UART_MSR_RI                     0x40    /* Ring Indicator */
 
103
#define UART_MSR_DSR                0x20        /* Data Set Ready */
 
104
#define UART_MSR_CTS                0x10        /* Clear to Send */
 
105
#define UART_MSR_DDCD               0x08        /* Delta DCD */
 
106
#define UART_MSR_TERI               0x04        /* Trailing edge ring indicator */
 
107
#define UART_MSR_DDSR               0x02        /* Delta DSR */
 
108
#define UART_MSR_DCTS               0x01        /* Delta CTS */
 
109
#define UART_MSR_ANY_DELTA          0x0F        /* Any of the delta bits! */
110
110
 
111
 
#define UART_LSR_TEMT               0x40        /* Transmitter empty */
112
 
#define UART_LSR_THRE               0x20        /* Transmit-hold-register empty */
113
 
#define UART_LSR_BI                     0x10    /* Break interrupt indicator */
114
 
#define UART_LSR_FE                     0x08    /* Frame error indicator */
115
 
#define UART_LSR_PE                     0x04    /* Parity error indicator */
116
 
#define UART_LSR_OE                     0x02    /* Overrun error indicator */
117
 
#define UART_LSR_DR                     0x01    /* Receiver data ready */
 
111
#define UART_LSR_TEMT               0x40        /* Transmitter empty */
 
112
#define UART_LSR_THRE               0x20        /* Transmit-hold-register empty */
 
113
#define UART_LSR_BI                     0x10    /* Break interrupt indicator */
 
114
#define UART_LSR_FE                     0x08    /* Frame error indicator */
 
115
#define UART_LSR_PE                     0x04    /* Parity error indicator */
 
116
#define UART_LSR_OE                     0x02    /* Overrun error indicator */
 
117
#define UART_LSR_DR                     0x01    /* Receiver data ready */
118
118
 
119
119
 
120
120
/*******************************************************************************
199
199
        s->iir = UART_IIR_THRI;
200
200
    } else if (s->msr_changed && (s->ier & UART_IER_RLSI)) {
201
201
        s->iir = UART_IIR_RLSI;
 
202
    } else if (s->lsr & UART_LSR_BI) {
 
203
        s->iir = 0; /* No special status bit */
202
204
    } else {
203
205
        s->iir = UART_IIR_NO_INT;
204
206
    }
307
309
            break_enable = (val >> 6) & 1;
308
310
            if (break_enable != s->last_break_enable) {
309
311
                s->last_break_enable = break_enable;
 
312
                if (RT_LIKELY(s->pDrvChar))
 
313
                {
 
314
                    Log(("serial_io_port_write: Set break %d\n", break_enable));
 
315
                    int rc = s->pDrvChar->pfnSetBreak(s->pDrvChar, !!break_enable);
 
316
                    AssertRC(rc);
 
317
                }
310
318
            }
311
319
        }
312
320
        break;
493
501
    return VINF_SUCCESS;
494
502
}
495
503
 
 
504
static DECLCALLBACK(int) serialNotifyBreak(PPDMICHARPORT pInterface)
 
505
{
 
506
    SerialState *pThis = PDMICHARPORT_2_SERIALSTATE(pInterface);
 
507
 
 
508
    Log(("%s: pInterface=%p\n", __FUNCTION__, pInterface));
 
509
 
 
510
    PDMCritSectEnter(&pThis->CritSect, VERR_PERMISSION_DENIED);
 
511
 
 
512
    pThis->lsr |= UART_LSR_BI;
 
513
    serial_update_irq(pThis);
 
514
 
 
515
    PDMCritSectLeave(&pThis->CritSect);
 
516
 
 
517
    return VINF_SUCCESS;
 
518
}
 
519
 
496
520
#endif /* IN_RING3 */
497
521
 
498
522
/**
564
588
#ifdef IN_RING3
565
589
 
566
590
/**
567
 
 * Saves a state of the serial port device.
568
 
 *
569
 
 * @returns VBox status code.
570
 
 * @param   pDevIns     The device instance.
571
 
 * @param   pSSMHandle  The handle to save the state to.
 
591
 * @copydoc FNSSMDEVLIVEEXEC
 
592
 */
 
593
static DECLCALLBACK(int) serialLiveExec(PPDMDEVINS pDevIns,
 
594
                                        PSSMHANDLE pSSM,
 
595
                                        uint32_t uPass)
 
596
{
 
597
    SerialState *pThis = PDMINS_2_DATA(pDevIns, SerialState *);
 
598
    SSMR3PutS32(pSSM, pThis->irq);
 
599
    SSMR3PutU32(pSSM, pThis->base);
 
600
    return VINF_SSM_DONT_CALL_AGAIN;
 
601
}
 
602
 
 
603
/**
 
604
 * @copydoc FNSSMDEVSAVEEXEC
572
605
 */
573
606
static DECLCALLBACK(int) serialSaveExec(PPDMDEVINS pDevIns,
574
 
                                        PSSMHANDLE pSSMHandle)
 
607
                                        PSSMHANDLE pSSM)
575
608
{
576
609
    SerialState *pThis = PDMINS_2_DATA(pDevIns, SerialState *);
577
610
 
578
 
    SSMR3PutU16(pSSMHandle, pThis->divider);
579
 
    SSMR3PutU8(pSSMHandle, pThis->rbr);
580
 
    SSMR3PutU8(pSSMHandle, pThis->ier);
581
 
    SSMR3PutU8(pSSMHandle, pThis->lcr);
582
 
    SSMR3PutU8(pSSMHandle, pThis->mcr);
583
 
    SSMR3PutU8(pSSMHandle, pThis->lsr);
584
 
    SSMR3PutU8(pSSMHandle, pThis->msr);
585
 
    SSMR3PutU8(pSSMHandle, pThis->scr);
586
 
    SSMR3PutS32(pSSMHandle, pThis->thr_ipending);
587
 
    SSMR3PutS32(pSSMHandle, pThis->irq);
588
 
    SSMR3PutS32(pSSMHandle, pThis->last_break_enable);
589
 
    SSMR3PutU32(pSSMHandle, pThis->base);
590
 
    SSMR3PutBool(pSSMHandle, pThis->msr_changed);
591
 
    return SSMR3PutU32(pSSMHandle, ~0); /* sanity/terminator */
 
611
    SSMR3PutU16(pSSM, pThis->divider);
 
612
    SSMR3PutU8(pSSM, pThis->rbr);
 
613
    SSMR3PutU8(pSSM, pThis->ier);
 
614
    SSMR3PutU8(pSSM, pThis->lcr);
 
615
    SSMR3PutU8(pSSM, pThis->mcr);
 
616
    SSMR3PutU8(pSSM, pThis->lsr);
 
617
    SSMR3PutU8(pSSM, pThis->msr);
 
618
    SSMR3PutU8(pSSM, pThis->scr);
 
619
    SSMR3PutS32(pSSM, pThis->thr_ipending);
 
620
    SSMR3PutS32(pSSM, pThis->irq);
 
621
    SSMR3PutS32(pSSM, pThis->last_break_enable);
 
622
    SSMR3PutU32(pSSM, pThis->base);
 
623
    SSMR3PutBool(pSSM, pThis->msr_changed);
 
624
    return SSMR3PutU32(pSSM, ~0); /* sanity/terminator */
592
625
}
593
626
 
594
627
/**
595
 
 * Loads a saved serial port device state.
596
 
 *
597
 
 * @returns VBox status code.
598
 
 * @param   pDevIns     The device instance.
599
 
 * @param   pSSMHandle  The handle to the saved state.
600
 
 * @param   u32Version  The data unit version number.
 
628
 * @copydoc FNSSMDEVLOADEXEC
601
629
 */
602
630
static DECLCALLBACK(int) serialLoadExec(PPDMDEVINS pDevIns,
603
 
                                        PSSMHANDLE pSSMHandle,
604
 
                                        uint32_t u32Version)
 
631
                                        PSSMHANDLE pSSM,
 
632
                                        uint32_t uVersion,
 
633
                                        uint32_t uPass)
605
634
{
606
 
    int          rc;
607
 
    uint32_t     u32;
608
635
    SerialState *pThis = PDMINS_2_DATA(pDevIns, SerialState *);
609
636
 
610
 
    if (u32Version != SERIAL_SAVED_STATE_VERSION)
611
 
    {
612
 
        AssertMsgFailed(("u32Version=%d\n", u32Version));
613
 
        return VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION;
614
 
    }
615
 
 
616
 
    SSMR3GetU16(pSSMHandle, &pThis->divider);
617
 
    SSMR3GetU8(pSSMHandle, &pThis->rbr);
618
 
    SSMR3GetU8(pSSMHandle, &pThis->ier);
619
 
    SSMR3GetU8(pSSMHandle, &pThis->lcr);
620
 
    SSMR3GetU8(pSSMHandle, &pThis->mcr);
621
 
    SSMR3GetU8(pSSMHandle, &pThis->lsr);
622
 
    SSMR3GetU8(pSSMHandle, &pThis->msr);
623
 
    SSMR3GetU8(pSSMHandle, &pThis->scr);
624
 
    SSMR3GetS32(pSSMHandle, &pThis->thr_ipending);
625
 
    SSMR3GetS32(pSSMHandle, &pThis->irq);
626
 
    SSMR3GetS32(pSSMHandle, &pThis->last_break_enable);
627
 
    SSMR3GetU32(pSSMHandle, &pThis->base);
628
 
    SSMR3GetBool(pSSMHandle, &pThis->msr_changed);
629
 
 
630
 
    rc = SSMR3GetU32(pSSMHandle, &u32);
631
 
    if (RT_FAILURE(rc))
632
 
        return rc;
633
 
 
634
 
    if (u32 != ~0U)
635
 
    {
636
 
        AssertLogRelMsgFailed(("u32=%#x expected ~0\n", u32));
637
 
        return VERR_SSM_DATA_UNIT_FORMAT_CHANGED;
638
 
    }
639
 
    /* Be careful with pointers in the structure; they are not preserved
640
 
     * in the saved state. */
641
 
 
642
 
    if (pThis->lsr & UART_LSR_DR)
643
 
    {
644
 
        int rc = RTSemEventSignal(pThis->ReceiveSem);
645
 
        AssertRC(rc);
646
 
    }
647
 
 
648
 
    /* this isn't strictly necessary but cannot hurt... */
649
 
    pThis->pDevInsR3 = pDevIns;
650
 
    pThis->pDevInsR0 = PDMDEVINS_2_R0PTR(pDevIns);
651
 
    pThis->pDevInsRC = PDMDEVINS_2_RCPTR(pDevIns);
 
637
    AssertMsgReturn(uVersion == SERIAL_SAVED_STATE_VERSION, ("%d\n", uVersion), VERR_SSM_UNSUPPORTED_DATA_UNIT_VERSION);
 
638
 
 
639
    if (uPass == SSM_PASS_FINAL)
 
640
    {
 
641
        SSMR3GetU16(pSSM, &pThis->divider);
 
642
        SSMR3GetU8(pSSM, &pThis->rbr);
 
643
        SSMR3GetU8(pSSM, &pThis->ier);
 
644
        SSMR3GetU8(pSSM, &pThis->lcr);
 
645
        SSMR3GetU8(pSSM, &pThis->mcr);
 
646
        SSMR3GetU8(pSSM, &pThis->lsr);
 
647
        SSMR3GetU8(pSSM, &pThis->msr);
 
648
        SSMR3GetU8(pSSM, &pThis->scr);
 
649
        SSMR3GetS32(pSSM, &pThis->thr_ipending);
 
650
    }
 
651
 
 
652
    int32_t  iIrq;
 
653
    SSMR3GetS32(pSSM, &iIrq);
 
654
 
 
655
    if (uPass == SSM_PASS_FINAL)
 
656
        SSMR3GetS32(pSSM, &pThis->last_break_enable);
 
657
 
 
658
    uint32_t IOBase;
 
659
    int rc = SSMR3GetU32(pSSM, &IOBase);
 
660
    AssertRCReturn(rc, rc);
 
661
 
 
662
    if (    pThis->irq  != iIrq
 
663
        ||  pThis->base != IOBase)
 
664
        return SSMR3SetCfgError(pSSM, RT_SRC_POS, N_("Config mismatch - saved irq=%#x iobase=%#x; configured irq=%#x iobase=%#x"),
 
665
                                iIrq, IOBase, pThis->irq, pThis->base);
 
666
 
 
667
    if (uPass == SSM_PASS_FINAL)
 
668
    {
 
669
        SSMR3GetBool(pSSM, &pThis->msr_changed);
 
670
 
 
671
        uint32_t u32;
 
672
        rc = SSMR3GetU32(pSSM, &u32);
 
673
        if (RT_FAILURE(rc))
 
674
            return rc;
 
675
        AssertMsgReturn(u32 == ~0U, ("%#x\n", u32), VERR_SSM_DATA_UNIT_FORMAT_CHANGED);
 
676
 
 
677
        if (pThis->lsr & UART_LSR_DR)
 
678
        {
 
679
            rc = RTSemEventSignal(pThis->ReceiveSem);
 
680
            AssertRC(rc);
 
681
        }
 
682
 
 
683
        /* this isn't strictly necessary but cannot hurt... */
 
684
        pThis->pDevInsR3 = pDevIns;
 
685
        pThis->pDevInsR0 = PDMDEVINS_2_R0PTR(pDevIns);
 
686
        pThis->pDevInsRC = PDMDEVINS_2_RCPTR(pDevIns);
 
687
    }
 
688
 
652
689
    return VINF_SUCCESS;
653
690
}
654
691
 
765
802
    pThis->IBase.pfnQueryInterface = serialQueryInterface;
766
803
 
767
804
    /* ICharPort */
768
 
    pThis->ICharPort.pfnNotifyRead = serialNotifyRead;
 
805
    pThis->ICharPort.pfnNotifyRead               = serialNotifyRead;
769
806
    pThis->ICharPort.pfnNotifyStatusLinesChanged = serialNotifyStatusLinesChanged;
 
807
    pThis->ICharPort.pfnNotifyBreak              = serialNotifyBreak;
770
808
 
771
809
#ifdef VBOX_SERIAL_PCI
772
810
    /* the PCI device */
881
919
        return rc;
882
920
 
883
921
    if (pThis->fGCEnabled)
 
922
    {
884
923
        rc = PDMDevHlpIOPortRegisterGC(pDevIns, io_base, 8, 0, "serialIOPortWrite",
885
924
                                      "serialIOPortRead", NULL, NULL, "Serial");
 
925
        if (RT_FAILURE(rc))
 
926
            return rc;
 
927
    }
 
928
 
886
929
 
887
930
    if (pThis->fR0Enabled)
 
931
    {
888
932
        rc = PDMDevHlpIOPortRegisterR0(pDevIns, io_base, 8, 0, "serialIOPortWrite",
889
933
                                      "serialIOPortRead", NULL, NULL, "Serial");
 
934
        if (RT_FAILURE(rc))
 
935
            return rc;
 
936
    }
890
937
#endif /* !VBOX_SERIAL_PCI */
891
938
 
892
939
    /*
893
940
     * Saved state.
894
941
     */
895
 
    rc = PDMDevHlpSSMRegister(
896
 
        pDevIns,                /* pDevIns */
897
 
        pDevIns->pDevReg->szDeviceName, /* pszName */
898
 
        iInstance,              /* u32Instance */
899
 
        SERIAL_SAVED_STATE_VERSION, /* u32Version */
900
 
        sizeof (*pThis),        /* cbGuess */
901
 
        NULL,                   /* pfnSavePrep */
902
 
        serialSaveExec,         /* pfnSaveExec */
903
 
        NULL,                   /* pfnSaveDone */
904
 
        NULL,                   /* pfnLoadPrep */
905
 
        serialLoadExec,         /* pfnLoadExec */
906
 
        NULL                    /* pfnLoadDone */
907
 
        );
 
942
    rc = PDMDevHlpSSMRegister3(pDevIns, SERIAL_SAVED_STATE_VERSION, sizeof (*pThis),
 
943
                               serialLiveExec, serialSaveExec, serialLoadExec);
908
944
    if (RT_FAILURE(rc))
909
945
        return rc;
910
946
 
960
996
    /* fClass */
961
997
    PDM_DEVREG_CLASS_SERIAL,
962
998
    /* cMaxInstances */
963
 
    1,
 
999
    UINT32_MAX,
964
1000
    /* cbInstance */
965
1001
    sizeof(SerialState),
966
1002
    /* pfnConstruct */