@@ -142,6 +142,10 @@ static u32 handle[] = {
142
142
143
143
static unsigned long dimm_fail_cmd_flags [ARRAY_SIZE (handle )];
144
144
static int dimm_fail_cmd_code [ARRAY_SIZE (handle )];
145
+ struct nfit_test_sec {
146
+ u8 state ;
147
+ u8 passphrase [32 ];
148
+ } dimm_sec_info [NUM_DCR ];
145
149
146
150
static const struct nd_intel_smart smart_def = {
147
151
.flags = ND_INTEL_SMART_HEALTH_VALID
@@ -933,6 +937,138 @@ static int override_return_code(int dimm, unsigned int func, int rc)
933
937
return rc ;
934
938
}
935
939
940
+ static int nd_intel_test_cmd_security_status (struct nfit_test * t ,
941
+ struct nd_intel_get_security_state * nd_cmd ,
942
+ unsigned int buf_len , int dimm )
943
+ {
944
+ struct device * dev = & t -> pdev .dev ;
945
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
946
+
947
+ nd_cmd -> status = 0 ;
948
+ nd_cmd -> state = sec -> state ;
949
+ dev_dbg (dev , "security state (%#x) returned\n" , nd_cmd -> state );
950
+
951
+ return 0 ;
952
+ }
953
+
954
+ static int nd_intel_test_cmd_unlock_unit (struct nfit_test * t ,
955
+ struct nd_intel_unlock_unit * nd_cmd ,
956
+ unsigned int buf_len , int dimm )
957
+ {
958
+ struct device * dev = & t -> pdev .dev ;
959
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
960
+
961
+ if (!(sec -> state & ND_INTEL_SEC_STATE_LOCKED ) ||
962
+ (sec -> state & ND_INTEL_SEC_STATE_FROZEN )) {
963
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_STATE ;
964
+ dev_dbg (dev , "unlock unit: invalid state: %#x\n" ,
965
+ sec -> state );
966
+ } else if (memcmp (nd_cmd -> passphrase , sec -> passphrase ,
967
+ ND_INTEL_PASSPHRASE_SIZE ) != 0 ) {
968
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_PASS ;
969
+ dev_dbg (dev , "unlock unit: invalid passphrase\n" );
970
+ } else {
971
+ nd_cmd -> status = 0 ;
972
+ sec -> state = ND_INTEL_SEC_STATE_ENABLED ;
973
+ dev_dbg (dev , "Unit unlocked\n" );
974
+ }
975
+
976
+ dev_dbg (dev , "unlocking status returned: %#x\n" , nd_cmd -> status );
977
+ return 0 ;
978
+ }
979
+
980
+ static int nd_intel_test_cmd_set_pass (struct nfit_test * t ,
981
+ struct nd_intel_set_passphrase * nd_cmd ,
982
+ unsigned int buf_len , int dimm )
983
+ {
984
+ struct device * dev = & t -> pdev .dev ;
985
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
986
+
987
+ if (sec -> state & ND_INTEL_SEC_STATE_FROZEN ) {
988
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_STATE ;
989
+ dev_dbg (dev , "set passphrase: wrong security state\n" );
990
+ } else if (memcmp (nd_cmd -> old_pass , sec -> passphrase ,
991
+ ND_INTEL_PASSPHRASE_SIZE ) != 0 ) {
992
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_PASS ;
993
+ dev_dbg (dev , "set passphrase: wrong passphrase\n" );
994
+ } else {
995
+ memcpy (sec -> passphrase , nd_cmd -> new_pass ,
996
+ ND_INTEL_PASSPHRASE_SIZE );
997
+ sec -> state |= ND_INTEL_SEC_STATE_ENABLED ;
998
+ nd_cmd -> status = 0 ;
999
+ dev_dbg (dev , "passphrase updated\n" );
1000
+ }
1001
+
1002
+ return 0 ;
1003
+ }
1004
+
1005
+ static int nd_intel_test_cmd_freeze_lock (struct nfit_test * t ,
1006
+ struct nd_intel_freeze_lock * nd_cmd ,
1007
+ unsigned int buf_len , int dimm )
1008
+ {
1009
+ struct device * dev = & t -> pdev .dev ;
1010
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
1011
+
1012
+ if (!(sec -> state & ND_INTEL_SEC_STATE_ENABLED )) {
1013
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_STATE ;
1014
+ dev_dbg (dev , "freeze lock: wrong security state\n" );
1015
+ } else {
1016
+ sec -> state |= ND_INTEL_SEC_STATE_FROZEN ;
1017
+ nd_cmd -> status = 0 ;
1018
+ dev_dbg (dev , "security frozen\n" );
1019
+ }
1020
+
1021
+ return 0 ;
1022
+ }
1023
+
1024
+ static int nd_intel_test_cmd_disable_pass (struct nfit_test * t ,
1025
+ struct nd_intel_disable_passphrase * nd_cmd ,
1026
+ unsigned int buf_len , int dimm )
1027
+ {
1028
+ struct device * dev = & t -> pdev .dev ;
1029
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
1030
+
1031
+ if (!(sec -> state & ND_INTEL_SEC_STATE_ENABLED ) ||
1032
+ (sec -> state & ND_INTEL_SEC_STATE_FROZEN )) {
1033
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_STATE ;
1034
+ dev_dbg (dev , "disable passphrase: wrong security state\n" );
1035
+ } else if (memcmp (nd_cmd -> passphrase , sec -> passphrase ,
1036
+ ND_INTEL_PASSPHRASE_SIZE ) != 0 ) {
1037
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_PASS ;
1038
+ dev_dbg (dev , "disable passphrase: wrong passphrase\n" );
1039
+ } else {
1040
+ memset (sec -> passphrase , 0 , ND_INTEL_PASSPHRASE_SIZE );
1041
+ sec -> state = 0 ;
1042
+ dev_dbg (dev , "disable passphrase: done\n" );
1043
+ }
1044
+
1045
+ return 0 ;
1046
+ }
1047
+
1048
+ static int nd_intel_test_cmd_secure_erase (struct nfit_test * t ,
1049
+ struct nd_intel_secure_erase * nd_cmd ,
1050
+ unsigned int buf_len , int dimm )
1051
+ {
1052
+ struct device * dev = & t -> pdev .dev ;
1053
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
1054
+
1055
+ if (!(sec -> state & ND_INTEL_SEC_STATE_ENABLED ) ||
1056
+ (sec -> state & ND_INTEL_SEC_STATE_FROZEN )) {
1057
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_STATE ;
1058
+ dev_dbg (dev , "secure erase: wrong security state\n" );
1059
+ } else if (memcmp (nd_cmd -> passphrase , sec -> passphrase ,
1060
+ ND_INTEL_PASSPHRASE_SIZE ) != 0 ) {
1061
+ nd_cmd -> status = ND_INTEL_STATUS_INVALID_PASS ;
1062
+ dev_dbg (dev , "secure erase: wrong passphrase\n" );
1063
+ } else {
1064
+ memset (sec -> passphrase , 0 , ND_INTEL_PASSPHRASE_SIZE );
1065
+ sec -> state = 0 ;
1066
+ dev_dbg (dev , "secure erase: done\n" );
1067
+ }
1068
+
1069
+ return 0 ;
1070
+ }
1071
+
936
1072
static int get_dimm (struct nfit_mem * nfit_mem , unsigned int func )
937
1073
{
938
1074
int i ;
@@ -980,6 +1116,30 @@ static int nfit_test_ctl(struct nvdimm_bus_descriptor *nd_desc,
980
1116
return i ;
981
1117
982
1118
switch (func ) {
1119
+ case NVDIMM_INTEL_GET_SECURITY_STATE :
1120
+ rc = nd_intel_test_cmd_security_status (t ,
1121
+ buf , buf_len , i );
1122
+ break ;
1123
+ case NVDIMM_INTEL_UNLOCK_UNIT :
1124
+ rc = nd_intel_test_cmd_unlock_unit (t ,
1125
+ buf , buf_len , i );
1126
+ break ;
1127
+ case NVDIMM_INTEL_SET_PASSPHRASE :
1128
+ rc = nd_intel_test_cmd_set_pass (t ,
1129
+ buf , buf_len , i );
1130
+ break ;
1131
+ case NVDIMM_INTEL_DISABLE_PASSPHRASE :
1132
+ rc = nd_intel_test_cmd_disable_pass (t ,
1133
+ buf , buf_len , i );
1134
+ break ;
1135
+ case NVDIMM_INTEL_FREEZE_LOCK :
1136
+ rc = nd_intel_test_cmd_freeze_lock (t ,
1137
+ buf , buf_len , i );
1138
+ break ;
1139
+ case NVDIMM_INTEL_SECURE_ERASE :
1140
+ rc = nd_intel_test_cmd_secure_erase (t ,
1141
+ buf , buf_len , i );
1142
+ break ;
983
1143
case ND_INTEL_ENABLE_LSS_STATUS :
984
1144
rc = nd_intel_test_cmd_set_lss_status (t ,
985
1145
buf , buf_len );
@@ -1313,10 +1473,22 @@ static ssize_t fail_cmd_code_store(struct device *dev, struct device_attribute *
1313
1473
}
1314
1474
static DEVICE_ATTR_RW (fail_cmd_code );
1315
1475
1476
+ static ssize_t lock_dimm_store (struct device * dev ,
1477
+ struct device_attribute * attr , const char * buf , size_t size )
1478
+ {
1479
+ int dimm = dimm_name_to_id (dev );
1480
+ struct nfit_test_sec * sec = & dimm_sec_info [dimm ];
1481
+
1482
+ sec -> state = ND_INTEL_SEC_STATE_ENABLED | ND_INTEL_SEC_STATE_LOCKED ;
1483
+ return size ;
1484
+ }
1485
+ static DEVICE_ATTR_WO (lock_dimm );
1486
+
1316
1487
static struct attribute * nfit_test_dimm_attributes [] = {
1317
1488
& dev_attr_fail_cmd .attr ,
1318
1489
& dev_attr_fail_cmd_code .attr ,
1319
1490
& dev_attr_handle .attr ,
1491
+ & dev_attr_lock_dimm .attr ,
1320
1492
NULL ,
1321
1493
};
1322
1494
@@ -2195,6 +2367,14 @@ static void nfit_test0_setup(struct nfit_test *t)
2195
2367
set_bit (ND_INTEL_FW_FINISH_UPDATE , & acpi_desc -> dimm_cmd_force_en );
2196
2368
set_bit (ND_INTEL_FW_FINISH_QUERY , & acpi_desc -> dimm_cmd_force_en );
2197
2369
set_bit (ND_INTEL_ENABLE_LSS_STATUS , & acpi_desc -> dimm_cmd_force_en );
2370
+ set_bit (NVDIMM_INTEL_GET_SECURITY_STATE ,
2371
+ & acpi_desc -> dimm_cmd_force_en );
2372
+ set_bit (NVDIMM_INTEL_SET_PASSPHRASE , & acpi_desc -> dimm_cmd_force_en );
2373
+ set_bit (NVDIMM_INTEL_DISABLE_PASSPHRASE ,
2374
+ & acpi_desc -> dimm_cmd_force_en );
2375
+ set_bit (NVDIMM_INTEL_UNLOCK_UNIT , & acpi_desc -> dimm_cmd_force_en );
2376
+ set_bit (NVDIMM_INTEL_FREEZE_LOCK , & acpi_desc -> dimm_cmd_force_en );
2377
+ set_bit (NVDIMM_INTEL_SECURE_ERASE , & acpi_desc -> dimm_cmd_force_en );
2198
2378
}
2199
2379
2200
2380
static void nfit_test1_setup (struct nfit_test * t )
0 commit comments