// u32 smu_service_req(smu_t smu, u32 id, smu_service_args_t *args); public smu_response SMUServiceReq(smu_t smu, Messages id, smu_service_args_t args) { smu_response serviceResponse = new smu_response(); uint response = 0x0; //smu_service_args_t args = *inArgs; // Debug information. Console.WriteLine("SMU_SERVICE REQ_ID: 0x{0:X}", id); Console.WriteLine("SMU_SERVICE REQ: arg0: 0x{0:X}, arg1: 0x{1:X}, arg2: 0x{2:X}, " + "arg3: 0x{3:X}, arg4: 0x{4:X}, arg5: 0x{5:X}", args.arg0, args.arg1, args.arg2, args.arg3, args.arg4, args.arg5); // Clear the response. hwOps.smn_reg_write(smu.nb, smu.rep, 0x0); // Pass arguments. hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 0), args.arg0); hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 1), args.arg1); hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 2), args.arg2); hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 3), args.arg3); hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 4), args.arg4); hwOps.smn_reg_write(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 5), args.arg5); // Send message ID. hwOps.smn_reg_write(smu.nb, smu.msg, (uint)id); // Wait until response has changed. //while (response == 0x0) //{ // response = hwOps.smn_reg_read(smu.nb, smu.rep); //} do { response = hwOps.smn_reg_read(smu.nb, smu.rep); } while (response == 0x0); // Read back arguments. args.arg0 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 0)); args.arg1 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 1)); args.arg2 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 2)); args.arg3 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 3)); args.arg4 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 4)); args.arg5 = hwOps.smn_reg_read(smu.nb, C2PMSG_ARGx_ADDR(smu.arg_base, 5)); // Response. Console.WriteLine("SMU_SERVICE REP: REP: 0x{0:X}, arg0: 0x{1:X}, arg1: 0x{2:X}, arg2: 0x{3:X}, " + "arg3: 0x{4:X}, arg4: 0x{5:X}, arg5: 0x{6:X}", response, args.arg0, args.arg1, args.arg2, args.arg3, args.arg4, args.arg5); Console.WriteLine(args.arg0); // Create smu_response object. serviceResponse.response = response; serviceResponse.args = args; //return response; return(serviceResponse); }
// void free_nb(nb_t nb); // SMU related methods. // smu_t get_smu(nb_t nb, int smu_type); public smu_t GetSMU(uint nb, SMU_TYPE smu_type) { // Create new SMU structure. smu_t smu = new smu_t(); // Test message response and arguments. //uint rep; smu_service_args_t arg = new smu_service_args_t(); // Fill the SMU information. smu.nb = nb; switch (smu_type) { case SMU_TYPE.TYPE_MP1: smu.msg = MP1_C2PMSG_MESSAGE_ADDR; smu.rep = MP1_C2PMSG_RESPONSE_ADDR; smu.arg_base = MP1_C2PMSG_ARG_BASE; break; case SMU_TYPE.TYPE_PSMU: smu.msg = PSMU_C2PMSG_MESSAGE_ADDR; smu.rep = PSMU_C2PMSG_RESPONSE_ADDR; smu.arg_base = PSMU_C2PMSG_ARG_BASE; break; default: Console.WriteLine("Failed to get SMU, unknown SMU_TYPE: " + smu_type); break; } // Send a test message. SMUResponseCode resp = (SMUResponseCode)SMUServiceReq(smu, Messages.TestMessage, arg).response; if (resp != SMUResponseCode.Result_OK) { Console.WriteLine("Failed to get SMU: {0}, test message REP: {1}", smu_type, resp); } Console.WriteLine("SMU_TYPE: {0}, Test message response: {1}", smu_type, resp); return(smu); }
/// <summary> /// /// </summary> /// <param name="ry"></param> /// <param name="id"></param> /// <param name="value"></param> /// <returns></returns> public bool ServiceRequest(ryzen_access ry, Messages id, int value) { // TODO: Ensure that the ryzen access object is suitable for use // (check all properties of the ryzen_access struct). if (initialised) { smu_service_args_t args = new smu_service_args_t(); args.arg0 = (uint)value; smu_response smuResp = accessSmu.SMUServiceReq(ry.mp1_smu, id, args); if (smuResp.response == 0x01) { Console.WriteLine("Successful SMU request - Response: {0}", smuResp.response); return(true); } Console.WriteLine("Failed SMU request - Response: {0}", smuResp.response); return(false); } Console.WriteLine("RyzenApi not initialised."); return(false); }
/// <summary> /// /// </summary> /// <returns></returns> public ryzen_access GetRyzenAccess() { // ryzen_access ry = new ryzen_access(); ry.use = true; if (!initialised) { ry.use = false; Console.WriteLine("RyzenApi not initialised."); return(ry); } // smu_service_args_t args = new smu_service_args_t(); // If the ryzen_access object is unusable, // then the pci_obj will be set to false. ry.pci_obj = accessSmu.InitialisePCIObj(); if (!ry.pci_obj) { ry.use = false; Console.WriteLine("Unable to get PCI Obj."); //return ry; } // GetNB will always return the same pci address (0x0)?. ry.nb = (uint)accessSmu.GetNB(ry.pci_obj); if (ry.nb != 0x0) { ry.use = false; Console.WriteLine("Unable to get NB Obj."); //return ry; } // TODO: smu_t will never be null, so check contents before continuing. // Set ry.mp1_smu.nb to 1 by default, GetSMU will provide new SMU set to 0. // If the get failed then nb will still be set to 1. ry.mp1_smu.nb = 1; ry.mp1_smu = accessSmu.GetSMU(ry.nb, SMU_TYPE.TYPE_MP1); if (ry.mp1_smu.nb == 1) { ry.use = false; Console.WriteLine("MP1_SMU nb still set to 1."); //return ry; } Console.WriteLine("PSMU nb set to: " + ry.mp1_smu.nb); // Similar process with psmu. ry.psmu.nb = 1; ry.psmu = accessSmu.GetSMU(ry.nb, SMU_TYPE.TYPE_PSMU); if (ry.psmu.nb == 1) { ry.use = false; Console.WriteLine("PSMU nb still set to 1."); //return ry; } Console.WriteLine("PSMU nb set to: " + ry.psmu.nb); // Check if the device is a Ryzen nb SMU. args = accessSmu.SMUServiceReq(ry.mp1_smu, Definitions.Messages.GetBiosIfVersion, args).args; Console.WriteLine(args.arg0); if (args.arg0 < 0x5) { ry.use = false; Console.WriteLine("Not a Ryzen NB SMU, BIOS Interface Version: 0x{0}", args.arg0); } // Return the ryzen access object. Console.WriteLine("Initialised and returning ryzen_access object."); return(ry); }