Changeset f77ede10 in mainline


Ignore:
Timestamp:
2024-07-08T19:16:38Z (2 weeks ago)
Author:
Jiri Svoboda <jiri@…>
Branches:
master
Children:
705b65ea, c4300ef
Parents:
878736e
Message:

Write data (floppy)

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/block/pc-floppy/pc-floppy.c

    r878736e rf77ede10  
    785785}
    786786
     787/** Perform Write Data command.
     788 *
     789 * @param drive Floppy drive
     790 * @param cyl Cylinder
     791 * @param head Head
     792 * @param sec Sector
     793 * @param buf Source buffer
     794 * @param buf_size Source buffer size
     795 *
     796 * @return EOK on success or an error code
     797 */
     798static errno_t pc_fdc_drive_write_data(pc_fdc_drive_t *drive,
     799    uint8_t cyl, uint8_t head, uint8_t sec, const void *buf, size_t buf_size)
     800{
     801        pc_fdc_t *fdc = drive->fdc;
     802        pc_fdc_cmd_data_t cmd;
     803        pc_fdc_cmd_status_t status;
     804        async_sess_t *sess;
     805        size_t csize;
     806        errno_t rc;
     807
     808        ddf_msg(LVL_NOTE, "pc_fdc_drive_write_data");
     809
     810        /* Copy data from source buffer to DMA buffer */
     811        csize = min(fdc->dma_buf_size, buf_size);
     812        memcpy(fdc->dma_buf, buf, csize);
     813
     814        sess = ddf_dev_parent_sess_get(fdc->dev);
     815        ddf_msg(LVL_NOTE, "hw_res_dma_channel_setup(sess=%p, chan=%d "
     816            "pa=%lu size=%zu", sess, fdc->dma, fdc->dma_buf_pa,
     817            fdc->dma_buf_size);
     818        rc = hw_res_dma_channel_setup(sess, fdc->dma, fdc->dma_buf_pa,
     819            fdc->dma_buf_size, DMA_MODE_WRITE | DMA_MODE_AUTO |
     820            DMA_MODE_ON_DEMAND);
     821        ddf_msg(LVL_NOTE, "hw_res_dma_channel_setup->%d", rc);
     822
     823        cmd.flags_cc = fcf_mf | fcc_write_data;
     824        cmd.hd_us = (head & 1) << 2 | 0x00 /* drive 0 */;
     825        cmd.cyl = cyl;
     826        cmd.head = head;
     827        cmd.rec = sec;
     828        cmd.number = 2; /* 512 bytes */
     829        cmd.eot = sec;
     830        cmd.gpl = 0x1b;
     831        cmd.dtl = 0xff;
     832
     833        ddf_msg(LVL_NOTE, "write data: send");
     834        rc = pc_fdc_send(fdc, &cmd, sizeof(cmd));
     835        if (rc != EOK) {
     836                ddf_msg(LVL_WARN, "Failed sending Write Data command.");
     837                return rc;
     838        }
     839
     840        ddf_msg(LVL_NOTE, "write data: get");
     841        rc = pc_fdc_get(fdc, &status, sizeof(status));
     842        if (rc != EOK) {
     843                ddf_msg(LVL_WARN, "Failed getting status for Write Data");
     844                return rc;
     845        }
     846
     847        ddf_msg(LVL_NOTE, "write data: DONE");
     848        ddf_msg(LVL_NOTE, "st0=0x%x st1=0x%x st2=0x%x cyl=%u head=%u rec=%u "
     849            "number=%u", status.st0, status.st1, status.st2,
     850            status.cyl, status.head, status.rec, status.number);
     851
     852        /* Check for success status */
     853        if ((status.st0 & fsr0_ic_mask) != 0)
     854                return EIO;
     855
     856        return EOK;
     857}
     858
    787859/** Perform Sense Interrupt Status command.
    788860 *
     
    925997        }
    926998
    927         /* Maximum number of blocks to transfer at the same time */
    928999        while (cnt > 0) {
    9291000                pc_fdc_drive_ba_to_chs(drive, ba, &cyl, &head, &sec);
     
    9731044    const void *buf, size_t size)
    9741045{
    975         return ENOTSUP;
     1046        pc_fdc_drive_t *drive = bd_srv_drive(bd);
     1047        uint8_t cyl, head, sec;
     1048        errno_t rc;
     1049
     1050        ddf_msg(LVL_NOTE, "pc_fdc_bd_write_blocks");
     1051
     1052        if (size < cnt * drive->sec_size) {
     1053                rc = EINVAL;
     1054                goto error;
     1055        }
     1056
     1057        while (cnt > 0) {
     1058                pc_fdc_drive_ba_to_chs(drive, ba, &cyl, &head, &sec);
     1059
     1060                /* Write one block */
     1061                rc = pc_fdc_drive_write_data(drive, cyl, head, sec, buf,
     1062                    drive->sec_size);
     1063                if (rc != EOK)
     1064                        goto error;
     1065
     1066                ++ba;
     1067                --cnt;
     1068                buf += drive->sec_size;
     1069        }
     1070
     1071        return EOK;
     1072error:
     1073        ddf_msg(LVL_NOTE, "pc_fdc_bd_write_blocks: rc=%d", rc);
     1074        return rc;
    9761075}
    9771076
Note: See TracChangeset for help on using the changeset viewer.