qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: Farhan Ali <alifm@linux.ibm.com>
To: "Jason J. Herne" <jjherne@linux.ibm.com>,
	qemu-devel@nongnu.org, qemu-s390x@nongnu.org, cohuck@redhat.com,
	pasic@linux.ibm.com, bjsdjshi@linux.ibm.com,
	borntraeger@de.ibm.com
Subject: Re: [Qemu-devel] [PATCH 10/15] s390-bios: Support for running format-0/1 channel programs
Date: Thu, 13 Dec 2018 11:54:03 -0500	[thread overview]
Message-ID: <ac55f276-c2aa-010b-000e-d5ba51c00f31@linux.ibm.com> (raw)
In-Reply-To: <1544623878-11248-11-git-send-email-jjherne@linux.ibm.com>



On 12/12/2018 09:11 AM, Jason J. Herne wrote:
> Add struct for format-0 ccws. Support executing format-0 channel
> programs and waiting for their completion before continuing execution.
> This will be used for real dasd ipl.
> 
> Add cu_type() to channel io library. This will be used to query control
> unit type which is used to determine if we are booting a virtio device or a
> real dasd device.
> 
> Signed-off-by: Jason J. Herne <jjherne@linux.ibm.com>
> ---
>   pc-bios/s390-ccw/cio.c      | 108 ++++++++++++++++++++++++++++++++++++++
>   pc-bios/s390-ccw/cio.h      | 124 ++++++++++++++++++++++++++++++++++++++++++--
>   pc-bios/s390-ccw/s390-ccw.h |   1 +
>   pc-bios/s390-ccw/start.S    |  33 +++++++++++-
>   4 files changed, 261 insertions(+), 5 deletions(-)
> 
> diff --git a/pc-bios/s390-ccw/cio.c b/pc-bios/s390-ccw/cio.c
> index 095f79b..9019250 100644
> --- a/pc-bios/s390-ccw/cio.c
> +++ b/pc-bios/s390-ccw/cio.c
> @@ -10,6 +10,7 @@
> 
>   #include "libc.h"
>   #include "s390-ccw.h"
> +#include "s390-arch.h"
>   #include "cio.h"
> 
>   static char chsc_page[PAGE_SIZE] __attribute__((__aligned__(PAGE_SIZE)));
> @@ -39,3 +40,110 @@ void enable_subchannel(SubChannelId schid)
>       schib.pmcw.ena = 1;
>       msch(schid, &schib);
>   }
> +
> +uint16_t cu_type(SubChannelId schid)
> +{
> +    Ccw1 sense_id_ccw;
> +    SenseId sense_data;
> +
> +    sense_id_ccw.cmd_code = CCW_CMD_SENSE_ID;
> +    sense_id_ccw.cda = ptr2u32(&sense_data);
> +    sense_id_ccw.count = sizeof(sense_data);
> +
> +    if (do_cio(schid, ptr2u32(&sense_id_ccw), CCW_FMT1)) {
> +        panic("Failed to run SenseID CCw\n");
> +    }
> +
> +    return sense_data.cu_type;
> +}
> +
> +void basic_sense(SubChannelId schid, SenseData *sd)
> +{
> +    Ccw1 senseCcw;
> +
> +    senseCcw.cmd_code = CCW_CMD_BASIC_SENSE;
> +    senseCcw.cda = ptr2u32(sd);
> +    senseCcw.count = sizeof(*sd);
> +
> +    if (do_cio(schid, ptr2u32(&senseCcw), CCW_FMT1)) {
> +        panic("Failed to run Basic Sense CCW\n");
> +    }
> +}
> +
> +static bool irb_error(Irb *irb)
> +{
> +    /* We have to ignore Incorrect Length (cstat == 0x40) indicators because
> +     * real devices expect a 24 byte SenseID  buffer, and virtio devices expect
> +     * a much larger buffer. Neither device type can tolerate a buffer size
> +     * different from what they expect so they set this indicator.
> +     */
> +    if (irb->scsw.cstat != 0x00 && irb->scsw.cstat != 0x40) {
> +        return true;
> +    }
> +    return irb->scsw.dstat != 0xc;
> +}
> +
> +/* Executes a channel program at a given subchannel. The request to run the
> + * channel program is sent to the subchannel, we then wait for the interrupt
> + * singaling completion of the I/O operation(s) perfomed by the channel
> + * program. Lastly we verify that the i/o operation completed without error and
> + * that the interrupt we received was for the subchannel used to run the
> + * channel program.
> + *
> + * Note: This function assumes it is running in an environment where no other
> + * cpus are generating or receiving I/O interrupts. So either run it in a
> + * single-cpu environment or make sure all other cpus are not doing I/O and
> + * have I/O interrupts masked off.
> + */
> +int do_cio(SubChannelId schid, uint32_t ccw_addr, int fmt)
> +{
> +    CmdOrb orb = {};
> +    Irb irb = {};
> +    SenseData sd;
> +    int rc, retries = 0;
> +
> +    IPL_assert(fmt == 0 || fmt == 1, "Invalid ccw format");
> +
> +    /* ccw_addr must be <= 24 bits and point to at least one whole ccw. */
> +    if (fmt == 0) {
> +        IPL_assert(ccw_addr <= 0xFFFFFF - 8, "Invalid ccw address");
> +    }
> +
> +    orb.fmt = fmt ;
> +    orb.pfch = 1;  /* QEMU's cio implementation requires prefetch */
> +    orb.c64 = 1;   /* QEMU's cio implementation requires 64-bit idaws */
> +    orb.lpm = 0xFF; /* All paths allowed */
> +    orb.cpa = ccw_addr;
> +
> +    while (true) {
> +        rc = ssch(schid, &orb);
> +        if (rc) {
> +            print_int("ssch failed with rc=", rc);
> +            break;
> +        }
> +
> +        consume_io_int();
> +
> +        /* Clear read */
> +        rc = tsch(schid, &irb);
> +        if (rc) {
> +            print_int("tsch failed with rc=", rc);
> +            break;
> +        }
> +
> +        if (!irb_error(&irb)) {
> +            break;
> +        }

Now that we enable i/o interrupts, do we still need drain_irqs function 
anymore? Maybe we could refactor that.

My question is more out of curiosity and I know it's out of the score 
for this patch series.

> +
> +        /* Unexpected unit check. Use sense to clear unit check then retry. */
> +        if (unit_check(&irb) && retries <= 2) {
> +            basic_sense(schid, &sd);
> +            retries++;
> +            continue;
> +        }
> +
> +        break;
> +    }
> +
> +    return rc;
> +}
> diff --git a/pc-bios/s390-ccw/cio.h b/pc-bios/s390-ccw/cio.h
> index 7b07d75..5c16635 100644
> --- a/pc-bios/s390-ccw/cio.h
> +++ b/pc-bios/s390-ccw/cio.h
> @@ -70,9 +70,46 @@ struct scsw {
>       __u16 count;
>   } __attribute__ ((packed));
> 
> -#define SCSW_FCTL_CLEAR_FUNC 0x1000
> -#define SCSW_FCTL_HALT_FUNC 0x2000
> +/* Function Control */
>   #define SCSW_FCTL_START_FUNC 0x4000
> +#define SCSW_FCTL_HALT_FUNC 0x2000
> +#define SCSW_FCTL_CLEAR_FUNC 0x1000
> +
> +/* Activity Control */
> +#define SCSW_ACTL_RESUME_PEND   0x0800
> +#define SCSW_ACTL_START_PEND    0x0400
> +#define SCSW_ACTL_HALT_PEND     0x0200
> +#define SCSW_ACTL_CLEAR_PEND    0x0100
> +#define SCSW_ACTL_CH_ACTIVE     0x0080
> +#define SCSW_ACTL_DEV_ACTIVE    0x0040
> +#define SCSW_ACTL_SUSPENDED     0x0020
> +
> +/* Status Control */
> +#define SCSW_SCTL_ALERT         0x0010
> +#define SCSW_SCTL_INTERMED      0x0008
> +#define SCSW_SCTL_PRIMARY       0x0004
> +#define SCSW_SCTL_SECONDARY     0x0002
> +#define SCSW_SCTL_STATUS_PEND   0x0001
> +
> +/* SCSW Device Status Flags */
> +#define SCSW_DSTAT_ATTN     0x80
> +#define SCSW_DSTAT_STATMOD  0x40
> +#define SCSW_DSTAT_CUEND    0x20
> +#define SCSW_DSTAT_BUSY     0x10
> +#define SCSW_DSTAT_CHEND    0x08
> +#define SCSW_DSTAT_DEVEND   0x04
> +#define SCSW_DSTAT_UCHK     0x02
> +#define SCSW_DSTAT_UEXCP    0x01
> +
> +/* SCSW Subchannel Status Flags */
> +#define SCSW_CSTAT_PCINT    0x80
> +#define SCSW_CSTAT_BADLEN   0x40
> +#define SCSW_CSTAT_PROGCHK  0x20
> +#define SCSW_CSTAT_PROTCHK  0x10
> +#define SCSW_CSTAT_CHDCHK   0x08
> +#define SCSW_CSTAT_CHCCHK   0x04
> +#define SCSW_CSTAT_ICCHK    0x02
> +#define SCSW_CSTAT_CHAINCHK 0x01
> 
>   /*
>    * subchannel information block
> @@ -127,7 +164,23 @@ struct tpi_info {
>       __u32 reserved4  : 12;
>   } __attribute__ ((packed, aligned(4)));
> 
> -/* channel command word (type 1) */
> +/* channel command word (format 0) */
> +typedef struct ccw0 {
> +    __u8 cmd_code;
> +    __u32 cda        : 24;
> +    __u32 chainData  : 1;
> +    __u32 chain      : 1;
> +    __u32 sli        : 1;
> +    __u32 skip       : 1;
> +    __u32 pci        : 1;
> +    __u32 ida        : 1;
> +    __u32 suspend    : 1;
> +    __u32 mida       : 1;
> +    __u8 reserved;
> +    __u16 count;
> +} __attribute__ ((packed, aligned(8))) Ccw0;
> +
> +/* channel command word (format 1) */
>   typedef struct ccw1 {
>       __u8 cmd_code;
>       __u8 flags;
> @@ -135,6 +188,10 @@ typedef struct ccw1 {
>       __u32 cda;
>   } __attribute__ ((packed, aligned(8))) Ccw1;
> 
> +/* do_cio() CCW formats */
> +#define CCW_FMT0                 0x00
> +#define CCW_FMT1                 0x01
> +
>   #define CCW_FLAG_DC              0x80
>   #define CCW_FLAG_CC              0x40
>   #define CCW_FLAG_SLI             0x20
> @@ -190,6 +247,9 @@ struct ciw {
>       __u16 count;
>   };
> 
> +#define CU_TYPE_VIRTIO          0x3832
> +#define CU_TYPE_DASD            0x3990
> +
>   /*
>    * sense-id response buffer layout
>    */
> @@ -205,6 +265,61 @@ typedef struct senseid {
>       struct ciw ciw[62];
>   }  __attribute__ ((packed, aligned(4))) SenseId;
> 
> +/* architected values for first sense byte */
> +#define SNS0_CMD_REJECT         0x80
> +#define SNS0_INTERVENTION_REQ   0x40
> +#define SNS0_BUS_OUT_CHECK      0x20
> +#define SNS0_EQUIPMENT_CHECK    0x10
> +#define SNS0_DATA_CHECK         0x08
> +#define SNS0_OVERRUN            0x04
> +#define SNS0_INCOMPL_DOMAIN     0x01
> +
> +/* architectured values for second sense byte */
> +#define SNS1_PERM_ERR           0x80
> +#define SNS1_INV_TRACK_FORMAT   0x40
> +#define SNS1_EOC                0x20
> +#define SNS1_MESSAGE_TO_OPER    0x10
> +#define SNS1_NO_REC_FOUND       0x08
> +#define SNS1_FILE_PROTECTED     0x04
> +#define SNS1_WRITE_INHIBITED    0x02
> +#define SNS1_INPRECISE_END      0x01
> +
> +/* architectured values for third sense byte */
> +#define SNS2_REQ_INH_WRITE      0x80
> +#define SNS2_CORRECTABLE        0x40
> +#define SNS2_FIRST_LOG_ERR      0x20
> +#define SNS2_ENV_DATA_PRESENT   0x10
> +#define SNS2_INPRECISE_END      0x04
> +
> +/* 24-byte Sense fmt/msg codes */
> +#define SENSE24_FMT_PROG_SYS    0x0
> +#define SENSE24_FMT_EQUIPMENT   0x2
> +#define SENSE24_FMT_CONTROLLER  0x3
> +#define SENSE24_FMT_MISC        0xF
> +
> +#define SENSE24_FMT0_MSG_RESET_NOTIFICATION 0x16
> +
> +/* basic sense response buffer layout */
> +typedef struct senseData {
> +    uint8_t status[3];
> +    uint8_t res_count;
> +    uint8_t phys_drive_id;
> +    uint8_t low_cyl_addr;
> +    uint8_t head_high_cyl_addr;
> +    uint8_t fmt_msg;
> +    uint64_t fmt_dependent_info[2];
> +    uint8_t reserved;
> +    uint8_t program_action_code;
> +    uint16_t config_info;
> +    uint8_t mcode_hicyl;
> +    uint8_t cyl_head_addr[3];
> +}  __attribute__ ((packed, aligned(4))) SenseData;
> +
> +#define SENSE24_GET_FMT(sd)     (sd->fmt_msg & 0xF0 >> 4)
> +#define SENSE24_GET_MSG(sd)     (sd->fmt_msg & 0x0F)
> +
> +#define unit_check(irb)     ((irb)->scsw.dstat & SCSW_DSTAT_UCHK)
> +
>   /* interruption response block */
>   typedef struct irb {
>       struct scsw scsw;
> @@ -215,6 +330,9 @@ typedef struct irb {
> 
>   int enable_mss_facility(void);
>   void enable_subchannel(SubChannelId schid);
> +uint16_t cu_type(SubChannelId schid);
> +void basic_sense(SubChannelId schid, SenseData *sd);
> +int do_cio(SubChannelId schid, uint32_t ccw_addr, int fmt);
> 
>   /*
>    * Some S390 specific IO instructions as inline
> diff --git a/pc-bios/s390-ccw/s390-ccw.h b/pc-bios/s390-ccw/s390-ccw.h
> index b39ee5d..11bce7d 100644
> --- a/pc-bios/s390-ccw/s390-ccw.h
> +++ b/pc-bios/s390-ccw/s390-ccw.h
> @@ -52,6 +52,7 @@ typedef unsigned long long __u64;
>   /* start.s */
>   void disabled_wait(void);
>   void consume_sclp_int(void);
> +void consume_io_int(void);
> 
>   /* main.c */
>   void panic(const char *string);
> diff --git a/pc-bios/s390-ccw/start.S b/pc-bios/s390-ccw/start.S
> index eb8d024..a48c38f 100644
> --- a/pc-bios/s390-ccw/start.S
> +++ b/pc-bios/s390-ccw/start.S
> @@ -65,12 +65,32 @@ consume_sclp_int:
>           /* prepare external call handler */
>           larl %r1, external_new_code
>           stg %r1, 0x1b8
> -        larl %r1, external_new_mask
> +        larl %r1, int_new_mask
>           mvc 0x1b0(8),0(%r1)
>           /* load enabled wait PSW */
>           larl %r1, enabled_wait_psw
>           lpswe 0(%r1)
> 
> +/*
> + * void consume_io_int(void)
> + *
> + * eats one I/O interrupt
> + */
> +        .globl consume_io_int
> +consume_io_int:
> +        /* enable I/O interrupts in cr0 */
> +        stctg 6,6,0(15)
> +        oi 4(15), 0xff
> +        lctlg 6,6,0(15)
> +        /* prepare external call handler */

shouldn't this be i/o call handler?

> +        larl %r1, io_new_code
> +        stg %r1, 0x1f8
> +        larl %r1, int_new_mask
> +        mvc 0x1f0(8),0(%r1)
> +        /* load enabled wait PSW */
> +        larl %r1, enabled_wait_psw
> +        lpswe 0(%r1)
> +
>   external_new_code:
>           /* disable service interrupts in cr0 */
>           stctg 0,0,0(15)
> @@ -78,10 +98,19 @@ external_new_code:
>           lctlg 0,0,0(15)
>           br 14
> 
> +io_new_code:
> +        /* disable I/O interrupts in cr6 */
> +        stctg 6,6,0(15)
> +        ni 4(15), 0x00
> +        lctlg 6,6,0(15)
> +        br 14
> +
> +
> +
>           .align  8
>   disabled_wait_psw:
>           .quad   0x0002000180000000,0x0000000000000000
>   enabled_wait_psw:
>           .quad   0x0302000180000000,0x0000000000000000
> -external_new_mask:
> +int_new_mask:
>           .quad   0x0000000180000000
> 

  reply	other threads:[~2018-12-13 16:54 UTC|newest]

Thread overview: 58+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-12-12 14:11 [Qemu-devel] [PATCH 00/15] s390: vfio-ccw dasd ipl support Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 01/15] s390 vfio-ccw: Add bootindex property and IPLB data Jason J. Herne
2018-12-12 15:22   ` [Qemu-devel] [qemu-s390x] " Jason J. Herne
2018-12-13 16:48   ` [Qemu-devel] " Cornelia Huck
2018-12-12 14:11 ` [Qemu-devel] [PATCH 02/15] s390-bios: decouple cio setup from virtio Jason J. Herne
2018-12-13 13:14   ` Farhan Ali
2018-12-12 14:11 ` [Qemu-devel] [PATCH 03/15] s390-bios: decouple common boot logic " Jason J. Herne
2018-12-13 13:17   ` Farhan Ali
2018-12-12 14:11 ` [Qemu-devel] [PATCH 04/15] s390-bios: Extend find_dev() for non-virtio devices Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 05/15] s390-bios: Factor finding boot device out of virtio code path Jason J. Herne
2018-12-13 13:55   ` Farhan Ali
2018-12-12 14:11 ` [Qemu-devel] [PATCH 06/15] s390-bios: Clean up cio.h Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 07/15] s390-bios: Decouple channel i/o logic from virtio Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 08/15] s390-bios: Map low core memory Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 09/15] s390-bios: ptr2u32 and u32toptr Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 10/15] s390-bios: Support for running format-0/1 channel programs Jason J. Herne
2018-12-13 16:54   ` Farhan Ali [this message]
2018-12-13 17:21   ` Cornelia Huck
2019-01-07 19:02     ` Jason J. Herne
2019-01-08 11:07       ` Cornelia Huck
2019-01-09 18:10       ` [Qemu-devel] [qemu-s390x] " Jason J. Herne
2019-01-09 18:34         ` Cornelia Huck
2019-01-09 20:01           ` Jason J. Herne
2019-01-10 12:15             ` Cornelia Huck
2019-01-10 15:02               ` Jason J. Herne
2019-01-10 15:21                 ` Cornelia Huck
2019-01-16 15:19           ` Jason J. Herne
2019-01-14 18:44       ` Jason J. Herne
2019-01-15  8:54         ` Cornelia Huck
2018-12-12 14:11 ` [Qemu-devel] [PATCH 11/15] s390-bios: cio error handling Jason J. Herne
2018-12-13 17:11   ` Farhan Ali
2018-12-13 17:26   ` Cornelia Huck
2018-12-12 14:11 ` [Qemu-devel] [PATCH 12/15] s390-bios: Refactor virtio to run channel programs via cio Jason J. Herne
2018-12-14 13:04   ` Cornelia Huck
2019-01-10 16:12     ` Jason J. Herne
2019-01-10 16:19       ` Cornelia Huck
2018-12-12 14:11 ` [Qemu-devel] [PATCH 13/15] s390-bios: Use control unit type to determine boot method Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 14/15] s390-bios: Add channel command codes/structs needed for dasd-ipl Jason J. Herne
2018-12-12 14:11 ` [Qemu-devel] [PATCH 15/15] s390-bios: Support booting from real dasd device Jason J. Herne
2018-12-12 14:34 ` [Qemu-devel] [PATCH 00/15] s390: vfio-ccw dasd ipl support Cornelia Huck
2018-12-12 14:47   ` Jason J. Herne
2019-01-08 16:37   ` Jason J. Herne
2019-01-08 17:36     ` [Qemu-devel] [qemu-s390x] " Halil Pasic
2019-01-09  9:57       ` Cornelia Huck
2018-12-12 20:28 ` [Qemu-devel] " no-reply
  -- strict thread matches above, loose matches on Subject: below --
2019-01-29 13:29 Jason J. Herne
2019-01-29 13:29 ` [Qemu-devel] [PATCH 10/15] s390-bios: Support for running format-0/1 channel programs Jason J. Herne
2019-01-31 17:31   ` Farhan Ali
2019-02-04 11:13     ` Cornelia Huck
2019-02-04 19:29       ` Farhan Ali
2019-02-05 10:18         ` Cornelia Huck
2019-02-12 13:10           ` Halil Pasic
2019-02-27 13:35           ` Jason J. Herne
2019-02-27 14:07             ` Cornelia Huck
2019-02-27 13:32       ` Jason J. Herne
2019-02-27 14:06         ` Cornelia Huck
2019-02-04 11:24   ` Cornelia Huck
2019-02-21 18:01     ` Jason J. Herne
2019-02-22  8:35       ` Cornelia Huck

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ac55f276-c2aa-010b-000e-d5ba51c00f31@linux.ibm.com \
    --to=alifm@linux.ibm.com \
    --cc=bjsdjshi@linux.ibm.com \
    --cc=borntraeger@de.ibm.com \
    --cc=cohuck@redhat.com \
    --cc=jjherne@linux.ibm.com \
    --cc=pasic@linux.ibm.com \
    --cc=qemu-devel@nongnu.org \
    --cc=qemu-s390x@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).