diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/scsi/osd/osd_initiator.c | 86 |
1 files changed, 86 insertions, 0 deletions
diff --git a/drivers/scsi/osd/osd_initiator.c b/drivers/scsi/osd/osd_initiator.c index b982d767bf99..6849f269cd1b 100644 --- a/drivers/scsi/osd/osd_initiator.c +++ b/drivers/scsi/osd/osd_initiator.c | |||
@@ -111,6 +111,14 @@ static osd_cdb_offset osd_req_encode_offset(struct osd_request *or, | |||
111 | OSDv1_OFFSET_MIN_SHIFT, OSD_OFFSET_MAX_SHIFT); | 111 | OSDv1_OFFSET_MIN_SHIFT, OSD_OFFSET_MAX_SHIFT); |
112 | } | 112 | } |
113 | 113 | ||
114 | static struct osd_security_parameters * | ||
115 | _osd_req_sec_params(struct osd_request *or) | ||
116 | { | ||
117 | struct osd_cdb *ocdb = &or->cdb; | ||
118 | |||
119 | return &ocdb->v1.sec_params; | ||
120 | } | ||
121 | |||
114 | void osd_dev_init(struct osd_dev *osdd, struct scsi_device *scsi_device) | 122 | void osd_dev_init(struct osd_dev *osdd, struct scsi_device *scsi_device) |
115 | { | 123 | { |
116 | memset(osdd, 0, sizeof(*osdd)); | 124 | memset(osdd, 0, sizeof(*osdd)); |
@@ -799,6 +807,64 @@ static int _osd_req_finalize_attr_page(struct osd_request *or) | |||
799 | return ret; | 807 | return ret; |
800 | } | 808 | } |
801 | 809 | ||
810 | static int _osd_req_finalize_data_integrity(struct osd_request *or, | ||
811 | bool has_in, bool has_out, const u8 *cap_key) | ||
812 | { | ||
813 | struct osd_security_parameters *sec_parms = _osd_req_sec_params(or); | ||
814 | int ret; | ||
815 | |||
816 | if (!osd_is_sec_alldata(sec_parms)) | ||
817 | return 0; | ||
818 | |||
819 | if (has_out) { | ||
820 | struct _osd_req_data_segment seg = { | ||
821 | .buff = &or->out_data_integ, | ||
822 | .total_bytes = sizeof(or->out_data_integ), | ||
823 | }; | ||
824 | unsigned pad; | ||
825 | |||
826 | or->out_data_integ.data_bytes = cpu_to_be64( | ||
827 | or->out.bio ? or->out.bio->bi_size : 0); | ||
828 | or->out_data_integ.set_attributes_bytes = cpu_to_be64( | ||
829 | or->set_attr.total_bytes); | ||
830 | or->out_data_integ.get_attributes_bytes = cpu_to_be64( | ||
831 | or->enc_get_attr.total_bytes); | ||
832 | |||
833 | sec_parms->data_out_integrity_check_offset = | ||
834 | osd_req_encode_offset(or, or->out.total_bytes, &pad); | ||
835 | |||
836 | ret = _req_append_segment(or, pad, &seg, or->out.last_seg, | ||
837 | &or->out); | ||
838 | if (ret) | ||
839 | return ret; | ||
840 | or->out.last_seg = NULL; | ||
841 | |||
842 | /* they are now all chained to request sign them all together */ | ||
843 | osd_sec_sign_data(&or->out_data_integ, or->out.req->bio, | ||
844 | cap_key); | ||
845 | } | ||
846 | |||
847 | if (has_in) { | ||
848 | struct _osd_req_data_segment seg = { | ||
849 | .buff = &or->in_data_integ, | ||
850 | .total_bytes = sizeof(or->in_data_integ), | ||
851 | }; | ||
852 | unsigned pad; | ||
853 | |||
854 | sec_parms->data_in_integrity_check_offset = | ||
855 | osd_req_encode_offset(or, or->in.total_bytes, &pad); | ||
856 | |||
857 | ret = _req_append_segment(or, pad, &seg, or->in.last_seg, | ||
858 | &or->in); | ||
859 | if (ret) | ||
860 | return ret; | ||
861 | |||
862 | or->in.last_seg = NULL; | ||
863 | } | ||
864 | |||
865 | return 0; | ||
866 | } | ||
867 | |||
802 | /* | 868 | /* |
803 | * osd_finalize_request and helpers | 869 | * osd_finalize_request and helpers |
804 | */ | 870 | */ |
@@ -919,6 +985,12 @@ int osd_finalize_request(struct osd_request *or, | |||
919 | } | 985 | } |
920 | } | 986 | } |
921 | 987 | ||
988 | ret = _osd_req_finalize_data_integrity(or, has_in, has_out, cap_key); | ||
989 | if (ret) | ||
990 | return ret; | ||
991 | |||
992 | osd_sec_sign_cdb(&or->cdb, cap_key); | ||
993 | |||
922 | or->request->cmd = or->cdb.buff; | 994 | or->request->cmd = or->cdb.buff; |
923 | or->request->cmd_len = _osd_req_cdb_len(or); | 995 | or->request->cmd_len = _osd_req_cdb_len(or); |
924 | 996 | ||
@@ -984,6 +1056,20 @@ void osd_set_caps(struct osd_cdb *cdb, const void *caps) | |||
984 | memcpy(&cdb->v1.caps, caps, OSDv1_CAP_LEN); | 1056 | memcpy(&cdb->v1.caps, caps, OSDv1_CAP_LEN); |
985 | } | 1057 | } |
986 | 1058 | ||
1059 | bool osd_is_sec_alldata(struct osd_security_parameters *sec_parms __unused) | ||
1060 | { | ||
1061 | return false; | ||
1062 | } | ||
1063 | |||
1064 | void osd_sec_sign_cdb(struct osd_cdb *ocdb __unused, const u8 *cap_key __unused) | ||
1065 | { | ||
1066 | } | ||
1067 | |||
1068 | void osd_sec_sign_data(void *data_integ __unused, | ||
1069 | struct bio *bio __unused, const u8 *cap_key __unused) | ||
1070 | { | ||
1071 | } | ||
1072 | |||
987 | /* | 1073 | /* |
988 | * Declared in osd_protocol.h | 1074 | * Declared in osd_protocol.h |
989 | * 4.12.5 Data-In and Data-Out buffer offsets | 1075 | * 4.12.5 Data-In and Data-Out buffer offsets |