Compare commits

...
Author SHA1 Message Date
Adam Honse 51edb35e3f Rework CoolerMaster ARGB controller so that it doesn't create multiple devices and prepare it for per-zone mode support 2026-03-04 11:45:48 -06:00
Adam Honse 81c6ee6270 Replace usages of sprintf with snprintf 2026-03-03 11:29:19 -06:00
Adam Honse 9ad37cc98f Fix logical error from changing type to unsigned 2026-03-03 11:25:22 -06:00
Adam Honse c76864dd4b Warning fixes and cleanups 2026-03-03 11:05:11 -06:00
Marco Martinez e3889508c0 Add support for another Airgoo Fan + DRGB Controller variant 2026-03-03 07:37:45 -06:00
Adam Honse 22d908b9a3 Fix warnings in ClevoLightbarController.cpp 2026-03-02 23:18:40 -06:00
Adam Honse 13d3e09f1a Fix warnings in ClevoKeyboardController.cpp 2026-03-02 23:17:23 -06:00
Adam Honse 9ec15673d1 Fix warnings in AsusMonitorController.cpp 2026-03-02 23:15:36 -06:00
Adam Honse 3a00a803e9 Fix warnings in LianLiUniHubSLController 2026-03-02 23:08:51 -06:00
Adam Honse 4a12a0db90 Fix warnings in LianLiUniversalScreenController 2026-03-02 23:07:12 -06:00
Adam Honse b4940e3a75 Fix warning in QMKVialRGBController 2026-03-02 23:04:40 -06:00
Adam Honse ffe07bbe3b Fix warning in RazerKrakenV3Controller 2026-03-02 23:03:00 -06:00
Adam Honse 7fdb006465 Fix warning in WootingV1KeyboardController 2026-03-02 23:01:29 -06:00
Adam Honse 99da577c41 Fix warning in SPDAccessor.cpp 2026-03-02 22:54:22 -06:00
Adam Honse 0f6fdd6c3b Fix warnings in HPOmenLaptopWMI_Windows 2026-03-02 22:52:12 -06:00
Adam Honse 52ec58d67f Fix warnings in NVFC nvapi.cpp 2026-03-02 22:44:19 -06:00
Adam Honse c55fc59d18 Clean up and fix warning in SteelSeriesApexController 2026-03-02 18:07:52 -06:00
Adam Honse b68b63e8c9 Fix warning in LianLiUniHubSLController 2026-03-02 16:16:10 -06:00
Kevin Ferrare 84bb05d504 Add support for MSI PRO B850M-P WIFI (MS-7E71) 2026-02-26 22:50:46 +01:00
Frans Meulenbroeks f33a7ba870 Mountain Everest 60: fix initialisation 2026-02-22 17:19:18 -06:00
chetrez911 93830c12ee Add support for MSI MAG B850 TOMAHAWK MAX WIFI (MS-7E62) 2026-02-22 11:56:23 -06:00
Arno b8b50f6651 Initial commit for MSI PRO Z790-S WIFI 2026-02-22 11:40:25 -06:00
sebastien ayanouglou 8f331090f9 Added support to RTX 5070Ti MSI Vanguard 16G 2026-02-16 07:21:32 -06:00
gozzarda 7ec1e8ddfa PowerColor GPU: Accept V1 magic from V2 controller. 2026-02-15 14:05:32 -06:00
Adam Honse 880dc1450d PNY ARGB Epic-X GPU: Add additional modes 2026-02-13 16:27:30 -06:00
Daenney 801e655c09 Add support for MSI MPG X870E EDGE TI WiFi 2026-02-13 13:36:54 -06:00
Adam Honse 5e269dd089 Add support for the PNY Epic-X ARGB 5070, 5080, and 5090 variants 2026-02-13 11:25:42 -06:00
John360Boxer 476f81d5e8 Initial commit for Redragon K686 Eisa Pro 2026-02-09 07:39:40 -06:00
storto 66dfb5f6fd Add/Fix support for the Gigabyte AORUS 5080 MASTER GPU 2026-02-08 12:45:02 -06:00
Michał Przytarski a2f2991192 feat: support MSI GeForce RTX 4060 GAMING X NV Edition 8G 2026-02-07 14:42:15 -06:00
Adam Honse cfedcd2180 Add Razer Blackwidow V4 Pro 75% wireless mode and add missing underglow LEDs to the matrix 2026-02-07 00:14:36 -06:00
Arthur de Groot cc06c62164 Rename Setting RunZoneChecks -> run_zone_checks 2026-02-05 17:20:14 -06:00
bernibaer b4ca000402 Initial support for Corsair K70 CORE TKL Keyboard ID 1b1c:2b01. Volume knob... 2026-01-30 13:49:48 -06:00
eriosgamer b78a6f4418 Fixed incorrect PID and device name. 2026-01-29 20:18:55 -06:00
Kirill Khakimov d5693b7a08 Add PCI device ID for Palit GeForce RTX 5070 Ti GamingPro-S 2026-01-29 16:54:41 -06:00
Werner Sembach cae0670065 Add new keynames 2026-01-29 16:18:13 -06:00
Adam Honse f2d1188fdd Fix swatches not resizing properly when maximized 2026-01-28 18:35:22 -06:00
Yohan 70be81c92d Merge: Add CDC Check in JGINYUE Usb Controller #5128 2026-01-27 10:54:51 -06:00
rszyma 5d5af93401 Add support for MSI PRO X870-P WIFI (MS-7E47) motherboard 2026-01-27 01:30:11 -06:00
superstrom 74cbdcce55 New Device: Razer Kraken Kitty V2 Pro 2026-01-25 17:40:54 -06:00
John Smith 96d19a76cc Add support for Sapphire Radeon RX 9060 XT Pure 2026-01-25 12:01:23 +03:00
68 changed files with 1595 additions and 1463 deletions
@@ -89,7 +89,7 @@ void AsusMonitorController::SetDirect(std::vector<RGBColor> colors)
usb_buf[0x00] = 0xEC;
usb_buf[0x01] = 0x40;
usb_buf[0x02] = 0x84;
usb_buf[0x04] = colors.size();
usb_buf[0x04] = (uint8_t)colors.size();
for(size_t i = 0; i < colors.size(); i++)
{
@@ -10,8 +10,9 @@
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#include "ClevoKeyboardController.h"
#include <cstring>
#include "ClevoKeyboardController.h"
#include "StringUtils.h"
ClevoKeyboardController::ClevoKeyboardController(hid_device* dev_handle, const hid_device_info& info)
{
@@ -40,10 +41,7 @@ std::string ClevoKeyboardController::GetSerialString()
return("");
}
std::wstring return_wstring = serial_string;
std::string return_string(return_wstring.begin(), return_wstring.end());
return(return_string);
return(StringUtils::wstring_to_string(serial_string));
}
std::string ClevoKeyboardController::GetFirmwareVersion()
@@ -10,8 +10,9 @@
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#include "ClevoLightbarController.h"
#include <cstring>
#include "ClevoLightbarController.h"
#include "StringUtils.h"
ClevoLightbarController::ClevoLightbarController(hid_device* dev_handle, const hid_device_info& info)
{
@@ -40,10 +41,7 @@ std::string ClevoLightbarController::GetSerialString()
return("");
}
std::wstring return_wstring = serial_string;
std::string return_string(return_wstring.begin(), return_wstring.end());
return(return_string);
return(StringUtils::wstring_to_string(serial_string));
}
std::string ClevoLightbarController::GetFirmwareVersion()
@@ -12,16 +12,27 @@
#include "CMARGBController.h"
#include "StringUtils.h"
CMARGBController::CMARGBController(hid_device* dev_handle, char *_path, unsigned char _zone_idx, std::shared_ptr<std::mutex> cm_mutex)
/*---------------------------------------------------------*\
| Map to convert port index to port ID used in protocol |
\*---------------------------------------------------------*/
static unsigned char cm_argb_port_index_to_id[5] =
{
dev = dev_handle;
location = _path;
zone_index = _zone_idx;
mutex_ptr = cm_mutex;
CM_ARGB_PORT_ARGB_1,
CM_ARGB_PORT_ARGB_2,
CM_ARGB_PORT_ARGB_3,
CM_ARGB_PORT_ARGB_4,
CM_ARGB_PORT_RGB
};
/*---------------------------------------------------------*\
| Get device name from HID manufacturer and product strings |
\*---------------------------------------------------------*/
CMARGBController::CMARGBController(hid_device* dev_handle, char *path)
{
dev = dev_handle;
location = path;
/*-----------------------------------------------------*\
| Get device name from HID manufacturer and product |
| strings |
\*-----------------------------------------------------*/
wchar_t name_string[HID_MAX_STR];
hid_get_manufacturer_string(dev, name_string, HID_MAX_STR);
@@ -29,57 +40,11 @@ CMARGBController::CMARGBController(hid_device* dev_handle, char *_path, unsigned
hid_get_product_string(dev, name_string, HID_MAX_STR);
device_name.append(" ").append(StringUtils::wstring_to_string(name_string));
GetStatus();
}
CMARGBController::~CMARGBController()
{
if(mutex_ptr.use_count() <= 1)
{
hid_close(dev);
}
}
void CMARGBController::GetStatus()
{
unsigned char buffer[CM_ARGB_PACKET_SIZE] = { 0x00, 0x80, 0x0B, 0x01 };
int buffer_size = (sizeof(buffer) / sizeof(buffer[0]));
int rgb_offset = 0;
int zone;
if (argb_header_data[zone_index].digital)
{
zone = argb_header_data[zone_index].header;
buffer[CM_ARGB_COMMAND_BYTE] = 0x0B;
}
else
{
zone = 0x00;
buffer[CM_ARGB_COMMAND_BYTE] = 0x0A;
rgb_offset = 1;
}
/*---------------------------------------------*\
| Guard the writes to the controller until the |
| for loop has completed to avoid collisons |
\*---------------------------------------------*/
std::lock_guard<std::mutex> guard(*mutex_ptr);
/*---------------------------------------------------------*\
| If this is the group then just return the first status |
\*---------------------------------------------------------*/
buffer[CM_ARGB_ZONE_BYTE] = ( zone > 0x08 ) ? 0x01 : zone;
hid_write(dev, buffer, buffer_size);
hid_read_timeout(dev, buffer, buffer_size, CM_ARGB_INTERRUPT_TIMEOUT);
current_mode = buffer[4 - rgb_offset];
bool_random = ( buffer[5 - rgb_offset] == 0x00 );
current_speed = buffer[6 - rgb_offset];
current_brightness = buffer[7 - rgb_offset];
current_red = buffer[8 - rgb_offset];
current_green = buffer[9 - rgb_offset];
current_blue = buffer[10 - rgb_offset];
hid_close(dev);
}
std::string CMARGBController::GetDeviceName()
@@ -87,6 +52,33 @@ std::string CMARGBController::GetDeviceName()
return(device_name);
}
std::string CMARGBController::GetLocation()
{
return("HID: " + location);
}
std::string CMARGBController::GetVersion()
{
/*-----------------------------------------------------*\
| This device uses the serial value to determine the |
| version. It does not report a proper unique serial. |
\*-----------------------------------------------------*/
std::string serial_string = GetSerial();
if(serial_string == CM_ARGB_FW0023)
{
return("0023");
}
else if(serial_string == CM_ARGB_FW0028)
{
return("0028");
}
else
{
return("Unsupported");
}
}
std::string CMARGBController::GetSerial()
{
wchar_t serial_string[HID_MAX_STR];
@@ -100,118 +92,187 @@ std::string CMARGBController::GetSerial()
return(StringUtils::wstring_to_string(serial_string));
}
std::string CMARGBController::GetLocation()
void CMARGBController::GetPortStatus
(
unsigned char port_idx,
unsigned char* port_mode,
unsigned char* port_speed,
unsigned char* port_brightness,
bool* port_random,
unsigned char* port_red,
unsigned char* port_green,
unsigned char* port_blue
)
{
return("HID: " + location);
unsigned char buffer[CM_ARGB_PACKET_SIZE] = {0x00, 0x80, 0x0B, 0x01};
int buffer_size = (sizeof(buffer) / sizeof(buffer[0]));
int rgb_offset = 0;
int zone;
/*-----------------------------------------------------*\
| RGB port is handled differently from ARGB ports |
\*-----------------------------------------------------*/
if(cm_argb_port_index_to_id[port_idx] != CM_ARGB_PORT_RGB)
{
zone = cm_argb_port_index_to_id[port_idx];
buffer[CM_ARGB_COMMAND_BYTE] = 0x0B;
}
else
{
zone = 0x00;
buffer[CM_ARGB_COMMAND_BYTE] = 0x0A;
rgb_offset = 1;
}
/*-----------------------------------------------------*\
| If this is the group then just return the first |
| status |
\*-----------------------------------------------------*/
buffer[CM_ARGB_ZONE_BYTE] = ( zone > 0x08 ) ? 0x01 : zone;
/*-----------------------------------------------------*\
| Send the command and read the response |
\*-----------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
hid_read_timeout(dev, buffer, buffer_size, CM_ARGB_INTERRUPT_TIMEOUT);
/*-----------------------------------------------------*\
| Read data out of response |
\*-----------------------------------------------------*/
*port_mode = buffer[4 - rgb_offset];
*port_random = (buffer[5 - rgb_offset] == 0x00);
*port_speed = buffer[6 - rgb_offset];
*port_brightness = buffer[7 - rgb_offset];
*port_red = buffer[8 - rgb_offset];
*port_green = buffer[9 - rgb_offset];
*port_blue = buffer[10 - rgb_offset];
}
unsigned char CMARGBController::GetZoneIndex()
void CMARGBController::SetPortLEDCount(unsigned char port_idx, unsigned char led_count)
{
return(zone_index);
}
unsigned char CMARGBController::GetMode()
{
return(current_mode);
}
unsigned char CMARGBController::GetLedRed()
{
return(current_red);
}
unsigned char CMARGBController::GetLedGreen()
{
return(current_green);
}
unsigned char CMARGBController::GetLedBlue()
{
return(current_blue);
}
unsigned char CMARGBController::GetLedSpeed()
{
return(current_speed);
}
bool CMARGBController::GetRandomColours()
{
return(bool_random);
}
void CMARGBController::SetLedCount(int zone, int led_count)
{
unsigned char buffer[CM_ARGB_PACKET_SIZE] = { 0x00, 0x80, 0x0D, 0x02 };
unsigned char buffer[CM_ARGB_PACKET_SIZE] = {0x00, 0x80, 0x0D, 0x02};
int buffer_size = (sizeof(buffer) / sizeof(buffer[0]));
buffer[CM_ARGB_ZONE_BYTE] = zone;
buffer[CM_ARGB_ZONE_BYTE] = cm_argb_port_index_to_id[port_idx];
buffer[CM_ARGB_MODE_BYTE] = led_count;
buffer[CM_ARGB_COLOUR_INDEX_BYTE] = (0x0F - led_count > 0) ? 0x0F - led_count : 0x01;
/*---------------------------------------------*\
| Guard the writes to the controller until the |
| for loop has completed to avoid collisons |
\*---------------------------------------------*/
std::lock_guard<std::mutex> guard(*mutex_ptr);
buffer[CM_ARGB_COLOUR_INDEX_BYTE] = 1;
/*-----------------------------------------------------*\
| Send the command |
\*-----------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
}
void CMARGBController::SetMode(uint8_t mode, uint8_t speed, uint8_t brightness, RGBColor colour, bool random_colours)
void CMARGBController::SetPortMode
(
unsigned char port_idx,
unsigned char port_mode,
unsigned char port_speed,
unsigned char port_brightness,
bool port_random,
unsigned char port_red,
unsigned char port_green,
unsigned char port_blue
)
{
bool needs_update = !( (current_mode == mode) && (current_speed == speed) && (current_brightness == brightness) && (ToRGBColor(current_red, current_green, current_blue) == colour));
unsigned char buffer[CM_ARGB_PACKET_SIZE] = {0x00};
int buffer_size = (sizeof(buffer) / sizeof(buffer[0]));
bool boolARGB_header = (cm_argb_port_index_to_id[port_idx] != CM_ARGB_PORT_RGB);
bool boolPassthru = (port_mode == CM_ARGB_MODE_PASSTHRU) || (port_mode == CM_RGB_MODE_PASSTHRU);
bool boolDirect = (port_mode == CM_ARGB_MODE_DIRECT);
unsigned char function = boolPassthru ? (boolARGB_header ? 0x02 : 0x04) : (boolARGB_header ? 0x01 : 0x03);
buffer[CM_ARGB_REPORT_BYTE] = 0x80;
buffer[CM_ARGB_COMMAND_BYTE] = 0x01;
if (needs_update)
if(boolDirect)
{
current_mode = mode;
current_speed = speed;
current_brightness = brightness;
current_red = RGBGetRValue(colour);
current_green = RGBGetGValue(colour);
current_blue = RGBGetBValue(colour);
bool_random = random_colours;
buffer[CM_ARGB_FUNCTION_BYTE] = 0x01;
buffer[CM_ARGB_ZONE_BYTE] = 0x02;
SendUpdate();
/*-------------------------------------------------*\
| Send the command |
\*-------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
/*-------------------------------------------------*\
| Direct mode is now set up and no other mode |
| packet is required |
\*-------------------------------------------------*/
return;
}
buffer[CM_ARGB_FUNCTION_BYTE] = function;
/*-----------------------------------------------------*\
| Send the command |
\*-----------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
/*-----------------------------------------------------*\
| ARGB ports send command 0x0B, RGB port sends 0x04 |
\*-----------------------------------------------------*/
if(boolARGB_header)
{
buffer[CM_ARGB_COMMAND_BYTE] = 0x0B;
buffer[CM_ARGB_FUNCTION_BYTE] = (false) ? 0x01 : 0x02;
buffer[CM_ARGB_ZONE_BYTE] = cm_argb_port_index_to_id[port_idx];
buffer[CM_ARGB_MODE_BYTE] = port_mode;
buffer[CM_ARGB_COLOUR_INDEX_BYTE] = port_random ? 0x00 : 0x10;
buffer[CM_ARGB_SPEED_BYTE] = port_speed;
buffer[CM_ARGB_BRIGHTNESS_BYTE] = port_brightness;
buffer[CM_ARGB_RED_BYTE] = port_red;
buffer[CM_ARGB_GREEN_BYTE] = port_green;
buffer[CM_ARGB_BLUE_BYTE] = port_blue;
}
else
{
buffer[CM_ARGB_COMMAND_BYTE] = boolPassthru ? 0x01 : 0x04;
buffer[CM_ARGB_MODE_BYTE + CM_RGB_OFFSET] = port_mode;
buffer[CM_ARGB_COLOUR_INDEX_BYTE + CM_RGB_OFFSET] = port_random ? 0x00 : 0x10;
buffer[CM_ARGB_SPEED_BYTE + CM_RGB_OFFSET] = port_speed;
buffer[CM_ARGB_BRIGHTNESS_BYTE + CM_RGB_OFFSET] = port_brightness;
buffer[CM_ARGB_RED_BYTE + CM_RGB_OFFSET] = port_red;
buffer[CM_ARGB_GREEN_BYTE + CM_RGB_OFFSET] = port_green;
buffer[CM_ARGB_BLUE_BYTE + CM_RGB_OFFSET] = port_blue;
}
/*-----------------------------------------------------*\
| Send the command and wait for response |
\*-----------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
}
void CMARGBController::SetLedsDirect(RGBColor *led_colours, unsigned int led_count)
void CMARGBController::SetPortLEDsDirect(unsigned char port_idx, RGBColor *led_colours, unsigned int led_count)
{
const unsigned char buffer_size = CM_ARGB_PACKET_SIZE;
unsigned char buffer[buffer_size] = { 0x00, 0x00, 0x07, 0x02 };
unsigned char packet_count = 0;
std::vector<uint8_t> colours;
/*---------------------------------------------*\
| Set up the RGB triplets to send |
\*---------------------------------------------*/
/*-----------------------------------------------------*\
| Set up the RGB triplets to send |
\*-----------------------------------------------------*/
for(unsigned int i = 0; i < led_count; i++)
{
RGBColor colour = led_colours[i];
colours.push_back( RGBGetRValue(colour) );
colours.push_back( RGBGetGValue(colour) );
colours.push_back( RGBGetBValue(colour) );
colours.push_back(RGBGetRValue(colour));
colours.push_back(RGBGetGValue(colour));
colours.push_back(RGBGetBValue(colour));
}
buffer[CM_ARGB_FUNCTION_BYTE] = zone_index - 1;
buffer[CM_ARGB_FUNCTION_BYTE] = port_idx;
buffer[CM_ARGB_ZONE_BYTE] = led_count;
unsigned char buffer_idx = CM_ARGB_MODE_BYTE;
/*---------------------------------------------*\
| Guard the writes to the controller until the |
| for loop has completed to avoid collisons |
\*---------------------------------------------*/
std::lock_guard<std::mutex> guard(*mutex_ptr);
for(std::vector<unsigned char>::iterator it = colours.begin(); it != colours.end(); buffer_idx = CM_ARGB_COMMAND_BYTE)
{
/*-----------------------------------------------------------------*\
| Fill the write buffer till its full or the colour buffer is empty |
\*-----------------------------------------------------------------*/
/*-------------------------------------------------*\
| Fill the write buffer till its full or the |
| colour buffer is empty |
\*-------------------------------------------------*/
buffer[CM_ARGB_REPORT_BYTE] = packet_count;
while (( buffer_idx < buffer_size) && ( it != colours.end() ))
while((buffer_idx < buffer_size) && (it != colours.end()))
{
buffer[buffer_idx] = *it;
buffer_idx++;
@@ -223,76 +284,15 @@ void CMARGBController::SetLedsDirect(RGBColor *led_colours, unsigned int led_cou
buffer[CM_ARGB_REPORT_BYTE] += 0x80;
}
/*-------------------------------------------------*\
| Send the buffer |
\*-------------------------------------------------*/
hid_write(dev, buffer, buffer_size);
/*-----------------------------------------------------------------*\
| Reset the write buffer |
\*-----------------------------------------------------------------*/
/*-------------------------------------------------*\
| Reset the write buffer |
\*-------------------------------------------------*/
memset(buffer, 0x00, buffer_size );
packet_count++;
}
}
void CMARGBController::SendUpdate()
{
/*---------------------------------------------*\
| Guard the writes to the controller |
\*---------------------------------------------*/
std::lock_guard<std::mutex> guard(*mutex_ptr);
unsigned char buffer[CM_ARGB_PACKET_SIZE] = { 0x00 };
int buffer_size = (sizeof(buffer) / sizeof(buffer[0]));
bool boolARGB_header = argb_header_data[zone_index].digital;
bool boolPassthru = ( current_mode == CM_ARGB_MODE_PASSTHRU ) || ( current_mode == CM_RGB_MODE_PASSTHRU );
bool boolDirect = ( current_mode == CM_ARGB_MODE_DIRECT );
unsigned char function = boolPassthru ? (boolARGB_header ? 0x02 : 0x04) : (boolARGB_header ? 0x01 : 0x03);
buffer[CM_ARGB_REPORT_BYTE] = 0x80;
buffer[CM_ARGB_COMMAND_BYTE] = 0x01;
if(boolDirect)
{
buffer[CM_ARGB_FUNCTION_BYTE] = 0x01;
buffer[CM_ARGB_ZONE_BYTE] = 0x02;
hid_write(dev, buffer, buffer_size);
hid_read_timeout(dev, buffer, buffer_size, CM_ARGB_INTERRUPT_TIMEOUT);
/*-----------------------------------------------------------------*\
| Direct mode is now set up and no other mode packet is required |
\*-----------------------------------------------------------------*/
return;
}
buffer[CM_ARGB_FUNCTION_BYTE] = function;
hid_write(dev, buffer, buffer_size);
hid_read_timeout(dev, buffer, buffer_size, CM_ARGB_INTERRUPT_TIMEOUT);
if(boolARGB_header)
{
buffer[CM_ARGB_COMMAND_BYTE] = 0x0B; //ARGB sends 0x0B (1011) RGB sends 0x04 (0100)
buffer[CM_ARGB_FUNCTION_BYTE] = (false) ? 0x01 : 0x02; //This controls direct mode TODO
buffer[CM_ARGB_ZONE_BYTE] = argb_header_data[zone_index].header;
buffer[CM_ARGB_MODE_BYTE] = current_mode;
buffer[CM_ARGB_COLOUR_INDEX_BYTE] = bool_random ? 0x00 : 0x10;
buffer[CM_ARGB_SPEED_BYTE] = current_speed;
buffer[CM_ARGB_BRIGHTNESS_BYTE] = current_brightness;
buffer[CM_ARGB_RED_BYTE] = current_red;
buffer[CM_ARGB_GREEN_BYTE] = current_green;
buffer[CM_ARGB_BLUE_BYTE] = current_blue;
}
else
{
buffer[CM_ARGB_COMMAND_BYTE] = boolPassthru ? 0x01 : 0x04; //ARGB sends 0x0b (1011) RGB sends 0x04 (0100)
buffer[CM_ARGB_MODE_BYTE + CM_RGB_OFFSET] = current_mode;
buffer[CM_ARGB_COLOUR_INDEX_BYTE + CM_RGB_OFFSET] = bool_random ? 0x00 : 0x10;
buffer[CM_ARGB_SPEED_BYTE + CM_RGB_OFFSET] = current_speed;
buffer[CM_ARGB_BRIGHTNESS_BYTE + CM_RGB_OFFSET] = current_brightness;
buffer[CM_ARGB_RED_BYTE + CM_RGB_OFFSET] = current_red;
buffer[CM_ARGB_GREEN_BYTE + CM_RGB_OFFSET] = current_green;
buffer[CM_ARGB_BLUE_BYTE + CM_RGB_OFFSET] = current_blue;
}
hid_write(dev, buffer, buffer_size);
hid_read_timeout(dev, buffer, buffer_size, CM_ARGB_INTERRUPT_TIMEOUT);
}
@@ -16,19 +16,20 @@
#include <array>
#include <memory>
#include <hidapi.h>
#include "RGBController.h" //Needed to set the direct mode
#include "RGBController.h"
#define CM_ARGB_COLOUR_MODE_DATA_SIZE (sizeof(colour_mode_data[0]) / sizeof(colour_mode_data[0][0]))
#define CM_ARGB_HEADER_DATA_SIZE (sizeof(argb_header_data) / sizeof(argb_headers) )
#define CM_ARGB_INTERRUPT_TIMEOUT 250
#define CM_ARGB_PACKET_SIZE 65
#define CM_ARGB_DEVICE_NAME_SIZE (sizeof(device_name) / sizeof(device_name[ 0 ]))
#define CM_RGB_OFFSET -2
#define HID_MAX_STR 255
#define CM_ARGB_COLOUR_MODE_DATA_SIZE (sizeof(colour_mode_data[0]) / sizeof(colour_mode_data[0][0]))
#define CM_ARGB_HEADER_DATA_SIZE (sizeof(argb_header_data) / sizeof(argb_headers) )
#define CM_ARGB_INTERRUPT_TIMEOUT 250
#define CM_ARGB_PACKET_SIZE 65
#define CM_ARGB_DEVICE_NAME_SIZE (sizeof(device_name) / sizeof(device_name[ 0 ]))
#define CM_RGB_OFFSET -2
#define HID_MAX_STR 255
#define CM_ARGB_BRIGHTNESS_MAX 255
#define CM_ARGB_FW0023 std::string("A202011171238")
#define CM_ARGB_FW0028 std::string("A202105291658")
#define CM_ARGB_BRIGHTNESS_MAX 255
#define CM_ARGB_FW0000 std::string("A201804091608")
#define CM_ARGB_FW0023 std::string("A202011171238")
#define CM_ARGB_FW0028 std::string("A202105291658")
enum
{
@@ -45,22 +46,13 @@ enum
CM_ARGB_BLUE_BYTE = 11
};
struct argb_headers
enum
{
const char* name;
unsigned char header;
bool digital;
unsigned int count;
};
static argb_headers argb_header_data[] =
{
{ "RGB Header", 0xFE, false, 1 },
{ "Digital ARGB1", 0x01, true, 12 },
{ "Digital ARGB2", 0x02, true, 12 },
{ "Digital ARGB3", 0x04, true, 12 },
{ "Digital ARGB4", 0x08, true, 12 },
//{ "All Digital ARGB", 0xFF, true, 12 }
CM_ARGB_PORT_ARGB_1 = 0x01,
CM_ARGB_PORT_ARGB_2 = 0x02,
CM_ARGB_PORT_ARGB_3 = 0x04,
CM_ARGB_PORT_ARGB_4 = 0x08,
CM_ARGB_PORT_RGB = 0xFE,
};
enum
@@ -101,40 +93,44 @@ enum
class CMARGBController
{
public:
CMARGBController(hid_device* dev_handle, char *_path, unsigned char _zone_idx, std::shared_ptr<std::mutex> cm_mutex);
CMARGBController(hid_device* dev_handle, char* path);
~CMARGBController();
std::string GetDeviceName();
std::string GetSerial();
std::string GetLocation();
std::string GetVersion();
unsigned char GetZoneIndex();
unsigned char GetMode();
unsigned char GetLedRed();
unsigned char GetLedGreen();
unsigned char GetLedBlue();
unsigned char GetLedSpeed();
bool GetRandomColours();
void SetLedCount(int zone, int led_count);
void SetMode(uint8_t mode, uint8_t speed, uint8_t brightness, RGBColor colour, bool random_colours);
void SetLedsDirect(RGBColor * led_colours, unsigned int led_count);
void GetPortStatus
(
unsigned char port_idx,
unsigned char* port_mode,
unsigned char* port_speed,
unsigned char* port_brightness,
bool* port_random,
unsigned char* port_red,
unsigned char* port_green,
unsigned char* port_blue
);
void SetPortLEDCount(unsigned char port_idx, unsigned char led_count);
void SetPortMode
(
unsigned char port_idx,
unsigned char port_mode,
unsigned char port_speed,
unsigned char port_brightness,
bool port_random,
unsigned char port_red,
unsigned char port_green,
unsigned char port_blue
);
void SetPortLEDsDirect(unsigned char port_idx, RGBColor *led_colours, unsigned int led_count);
private:
std::string device_name;
std::string location;
hid_device* dev;
std::shared_ptr<std::mutex> mutex_ptr;
unsigned char zone_index;
unsigned char current_mode;
unsigned char current_speed;
unsigned char current_red;
unsigned char current_green;
unsigned char current_blue;
unsigned char current_brightness;
bool bool_random;
void GetStatus();
void SendUpdate();
hid_device* dev;
std::string device_name;
std::string location;
};
@@ -27,268 +27,220 @@
RGBController_CMARGBController::RGBController_CMARGBController(CMARGBController* controller_ptr)
{
controller = controller_ptr;
unsigned char speed = controller->GetLedSpeed();
name = argb_header_data[controller->GetZoneIndex()].name;
name = controller->GetDeviceName();
vendor = "Cooler Master";
type = DEVICE_TYPE_LEDSTRIP;
description = controller->GetDeviceName();
version = "3.0 for FW0028";
description = "Cooler Master ARGB Controller Device";
version = controller->GetVersion();
serial = controller->GetSerial();
location = controller->GetLocation();
if(argb_header_data[controller->GetZoneIndex()].digital)
{
mode Off;
Off.name = "Turn Off";
Off.value = CM_ARGB_MODE_OFF;
Off.color_mode = MODE_COLORS_NONE;
modes.push_back(Off);
/*-----------------------------------------------------*\
| The ARGB ports support more modes than the RGB port. |
| Define all of the modes the ARGB ports support and |
| map RGB modes to them as best as we can. Per-zone |
| support will be added in the future. |
\*-----------------------------------------------------*/
mode Off;
Off.name = "Off";
Off.value = CM_ARGB_MODE_OFF;
Off.color_mode = MODE_COLORS_NONE;
modes.push_back(Off);
mode Reload;
Reload.name = "Reload";
Reload.value = CM_ARGB_MODE_RELOAD;
Reload.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Reload.colors_min = 1;
Reload.colors_max = 1;
Reload.colors.resize(Reload.colors_max);
Reload.brightness_min = 0;
Reload.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Reload.brightness = CM_ARGB_BRIGHTNESS_MAX;
Reload.speed_min = CM_ARGB_SPEED_SLOWEST;
Reload.speed_max = CM_ARGB_SPEED_FASTEST;
Reload.color_mode = MODE_COLORS_MODE_SPECIFIC;
Reload.speed = speed;
modes.push_back(Reload);
mode Reload;
Reload.name = "Reload";
Reload.value = CM_ARGB_MODE_RELOAD;
Reload.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Reload.speed_min = CM_ARGB_SPEED_SLOWEST;
Reload.speed_max = CM_ARGB_SPEED_FASTEST;
Reload.speed = CM_ARGB_SPEED_NORMAL;
Reload.brightness_min = 0;
Reload.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Reload.brightness = CM_ARGB_BRIGHTNESS_MAX;
Reload.color_mode = MODE_COLORS_MODE_SPECIFIC;
Reload.colors_min = 1;
Reload.colors_max = 1;
Reload.colors.resize(Reload.colors_max);
modes.push_back(Reload);
mode Recoil;
Recoil.name = "Recoil";
Recoil.value = CM_ARGB_MODE_RECOIL;
Recoil.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Recoil.colors_min = 1;
Recoil.colors_max = 1;
Recoil.colors.resize(Recoil.colors_max);
Recoil.brightness_min = 0;
Recoil.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Recoil.brightness = CM_ARGB_BRIGHTNESS_MAX;
Recoil.speed_min = CM_ARGB_SPEED_SLOWEST;
Recoil.speed_max = CM_ARGB_SPEED_FASTEST;
Recoil.color_mode = MODE_COLORS_MODE_SPECIFIC;
Recoil.speed = speed;
modes.push_back(Recoil);
mode Recoil;
Recoil.name = "Recoil";
Recoil.value = CM_ARGB_MODE_RECOIL;
Recoil.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Recoil.color_mode = MODE_COLORS_MODE_SPECIFIC;
Recoil.speed_min = CM_ARGB_SPEED_SLOWEST;
Recoil.speed_max = CM_ARGB_SPEED_FASTEST;
Recoil.speed = CM_ARGB_SPEED_NORMAL;
Recoil.brightness_min = 0;
Recoil.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Recoil.brightness = CM_ARGB_BRIGHTNESS_MAX;
Recoil.colors_min = 1;
Recoil.colors_max = 1;
Recoil.colors.resize(Recoil.colors_max);
modes.push_back(Recoil);
mode Breathing;
Breathing.name = "Breathing";
Breathing.value = CM_ARGB_MODE_BREATHING;
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Breathing.colors_min = 1;
Breathing.colors_max = 1;
Breathing.colors.resize(Breathing.colors_max);
Breathing.brightness_min = 0;
Breathing.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Breathing.brightness = CM_ARGB_BRIGHTNESS_MAX;
Breathing.speed_min = CM_ARGB_SPEED_SLOWEST;
Breathing.speed_max = CM_ARGB_SPEED_FASTEST;
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
Breathing.speed = speed;
modes.push_back(Breathing);
mode Breathing;
Breathing.name = "Breathing";
Breathing.value = CM_ARGB_MODE_BREATHING;
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
Breathing.speed_min = CM_ARGB_SPEED_SLOWEST;
Breathing.speed_max = CM_ARGB_SPEED_FASTEST;
Breathing.speed = CM_ARGB_SPEED_NORMAL;
Breathing.brightness_min = 0;
Breathing.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Breathing.brightness = CM_ARGB_BRIGHTNESS_MAX;
Breathing.colors_min = 1;
Breathing.colors_max = 1;
Breathing.colors.resize(Breathing.colors_max);
modes.push_back(Breathing);
mode Refill;
Refill.name = "Refill";
Refill.value = CM_ARGB_MODE_REFILL;
Refill.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Refill.colors_min = 1;
Refill.colors_max = 1;
Refill.colors.resize(Refill.colors_max);
Refill.brightness_min = 0;
Refill.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Refill.brightness = CM_ARGB_BRIGHTNESS_MAX;
Refill.speed_min = CM_ARGB_SPEED_SLOWEST;
Refill.speed_max = CM_ARGB_SPEED_FASTEST;
Refill.color_mode = MODE_COLORS_MODE_SPECIFIC;
Refill.speed = speed;
modes.push_back(Refill);
mode Refill;
Refill.name = "Refill";
Refill.value = CM_ARGB_MODE_REFILL;
Refill.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Refill.color_mode = MODE_COLORS_MODE_SPECIFIC;
Refill.speed_min = CM_ARGB_SPEED_SLOWEST;
Refill.speed_max = CM_ARGB_SPEED_FASTEST;
Refill.speed = CM_ARGB_SPEED_NORMAL;
Refill.brightness_min = 0;
Refill.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Refill.brightness = CM_ARGB_BRIGHTNESS_MAX;
Refill.colors_min = 1;
Refill.colors_max = 1;
Refill.colors.resize(Refill.colors_max);
modes.push_back(Refill);
mode Demo;
Demo.name = "Demo";
Demo.value = CM_ARGB_MODE_DEMO;
Demo.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Demo.brightness_min = 0;
Demo.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Demo.brightness = CM_ARGB_BRIGHTNESS_MAX;
Demo.speed_min = CM_ARGB_SPEED_SLOWEST;
Demo.speed_max = CM_ARGB_SPEED_FASTEST;
Demo.color_mode = MODE_COLORS_NONE;
Demo.speed = speed;
modes.push_back(Demo);
mode Demo;
Demo.name = "Demo";
Demo.value = CM_ARGB_MODE_DEMO;
Demo.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Demo.color_mode = MODE_COLORS_NONE;
Demo.speed_min = CM_ARGB_SPEED_SLOWEST;
Demo.speed_max = CM_ARGB_SPEED_FASTEST;
Demo.speed = CM_ARGB_SPEED_NORMAL;
Demo.brightness_min = 0;
Demo.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Demo.brightness = CM_ARGB_BRIGHTNESS_MAX;
modes.push_back(Demo);
mode Spectrum;
Spectrum.name = "Spectrum";
Spectrum.value = CM_ARGB_MODE_SPECTRUM;
Spectrum.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Spectrum.brightness_min = 0;
Spectrum.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Spectrum.brightness = CM_ARGB_BRIGHTNESS_MAX;
Spectrum.speed_min = CM_ARGB_SPEED_SLOWEST;
Spectrum.speed_max = CM_ARGB_SPEED_FASTEST;
Spectrum.color_mode = MODE_COLORS_NONE;
Spectrum.speed = speed;
modes.push_back(Spectrum);
mode Spectrum;
Spectrum.name = "Rainbow Wave";
Spectrum.value = CM_ARGB_MODE_SPECTRUM;
Spectrum.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Spectrum.color_mode = MODE_COLORS_NONE;
Spectrum.speed_min = CM_ARGB_SPEED_SLOWEST;
Spectrum.speed_max = CM_ARGB_SPEED_FASTEST;
Spectrum.speed = CM_ARGB_SPEED_NORMAL;
Spectrum.brightness_min = 0;
Spectrum.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Spectrum.brightness = CM_ARGB_BRIGHTNESS_MAX;
modes.push_back(Spectrum);
mode FillFlow;
FillFlow.name = "Fill Flow";
FillFlow.value = CM_ARGB_MODE_FILLFLOW;
FillFlow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
FillFlow.brightness_min = 0;
FillFlow.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
FillFlow.brightness = CM_ARGB_BRIGHTNESS_MAX;
FillFlow.speed_min = CM_ARGB_SPEED_SLOWEST;
FillFlow.speed_max = CM_ARGB_SPEED_FASTEST;
FillFlow.color_mode = MODE_COLORS_NONE;
FillFlow.speed = speed;
modes.push_back(FillFlow);
mode FillFlow;
FillFlow.name = "Fill Flow";
FillFlow.value = CM_ARGB_MODE_FILLFLOW;
FillFlow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
FillFlow.color_mode = MODE_COLORS_NONE;
FillFlow.speed_min = CM_ARGB_SPEED_SLOWEST;
FillFlow.speed_max = CM_ARGB_SPEED_FASTEST;
FillFlow.speed = CM_ARGB_SPEED_NORMAL;
FillFlow.brightness_min = 0;
FillFlow.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
FillFlow.brightness = CM_ARGB_BRIGHTNESS_MAX;
modes.push_back(FillFlow);
mode Rainbow;
Rainbow.name = "Rainbow";
Rainbow.value = CM_ARGB_MODE_RAINBOW;
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Rainbow.brightness_min = 0;
Rainbow.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Rainbow.brightness = CM_ARGB_BRIGHTNESS_MAX;
Rainbow.speed_min = CM_ARGB_SPEED_SLOWEST;
Rainbow.speed_max = CM_ARGB_SPEED_FASTEST;
Rainbow.color_mode = MODE_COLORS_NONE;
Rainbow.speed = speed;
modes.push_back(Rainbow);
mode Rainbow;
Rainbow.name = "Rainbow";
Rainbow.value = CM_ARGB_MODE_RAINBOW;
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Rainbow.color_mode = MODE_COLORS_NONE;
Rainbow.speed_min = CM_ARGB_SPEED_SLOWEST;
Rainbow.speed_max = CM_ARGB_SPEED_FASTEST;
Rainbow.speed = CM_ARGB_SPEED_NORMAL;
Rainbow.brightness_min = 0;
Rainbow.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Rainbow.brightness = CM_ARGB_BRIGHTNESS_MAX;
modes.push_back(Rainbow);
mode Static;
Static.name = "Static";
Static.value = CM_ARGB_MODE_STATIC;
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Static.colors_min = 1;
Static.colors_max = 1;
Static.colors.resize(Static.colors_max);
Static.brightness_min = 0;
Static.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Static.brightness = CM_ARGB_BRIGHTNESS_MAX;
Static.speed_min = CM_ARGB_SPEED_SLOWEST;
Static.speed_max = CM_ARGB_SPEED_FASTEST;
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
Static.speed = speed;
modes.push_back(Static);
mode Static;
Static.name = "Static";
Static.value = CM_ARGB_MODE_STATIC;
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
Static.speed_min = CM_ARGB_SPEED_SLOWEST;
Static.speed_max = CM_ARGB_SPEED_FASTEST;
Static.speed = CM_ARGB_SPEED_NORMAL;
Static.brightness_min = 0;
Static.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Static.brightness = CM_ARGB_BRIGHTNESS_MAX;
Static.colors_min = 1;
Static.colors_max = 1;
Static.colors.resize(Static.colors_max);
modes.push_back(Static);
mode Direct;
Direct.name = (serial >= CM_ARGB_FW0028) ? "Direct" : "Custom";
Direct.value = CM_ARGB_MODE_DIRECT;
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
Direct.color_mode = MODE_COLORS_PER_LED;
modes.push_back(Direct);
mode Direct;
Direct.name = (serial >= CM_ARGB_FW0028) ? "Direct" : "Custom";
Direct.value = CM_ARGB_MODE_DIRECT;
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
Direct.color_mode = MODE_COLORS_PER_LED;
modes.push_back(Direct);
mode PassThru;
PassThru.name = "Pass Thru";
PassThru.value = CM_ARGB_MODE_PASSTHRU;
PassThru.flags = 0;
PassThru.color_mode = MODE_COLORS_NONE;
modes.push_back(PassThru);
}
else
{
mode Static;
Static.name = "Static";
Static.value = CM_RGB_MODE_STATIC;
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Static.colors_min = 1;
Static.colors_max = 1;
Static.colors.resize(Static.colors_max);
Static.brightness_min = 0;
Static.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Static.brightness = CM_ARGB_BRIGHTNESS_MAX;
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
Static.speed = 0;
modes.push_back(Static);
mode PassThru;
PassThru.name = "Pass Thru";
PassThru.value = CM_ARGB_MODE_PASSTHRU;
PassThru.flags = 0;
PassThru.color_mode = MODE_COLORS_NONE;
modes.push_back(PassThru);
mode Breathing;
Breathing.name = "Breathing";
Breathing.value = CM_RGB_MODE_BREATHING;
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Breathing.colors_min = 1;
Breathing.colors_max = 1;
Breathing.colors.resize(Breathing.colors_max);
Breathing.brightness_min = 0;
Breathing.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Breathing.brightness = CM_ARGB_BRIGHTNESS_MAX;
Breathing.speed_min = CM_ARGB_SPEED_SLOWEST;
Breathing.speed_max = CM_ARGB_SPEED_FASTEST;
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
Breathing.speed = CM_ARGB_SPEED_NORMAL;
modes.push_back(Breathing);
mode Flash;
Flash.name = "Flash";
Flash.value = CM_RGB_MODE_FLASH;
Flash.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Flash.colors_min = 1;
Flash.colors_max = 1;
Flash.colors.resize(Flash.colors_max);
Flash.brightness_min = 0;
Flash.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Flash.brightness = CM_ARGB_BRIGHTNESS_MAX;
Flash.speed_min = CM_ARGB_SPEED_SLOWEST;
Flash.speed_max = CM_ARGB_SPEED_FASTEST;
Flash.color_mode = MODE_COLORS_MODE_SPECIFIC;
Flash.speed = CM_ARGB_SPEED_NORMAL;
modes.push_back(Flash);
mode Mirage;
Mirage.name = "Mirage";
Mirage.value = CM_RGB_MODE_MIRAGE;
Mirage.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
Mirage.colors_min = 1;
Mirage.colors_max = 1;
Mirage.colors.resize(Mirage.colors_max);
Mirage.brightness_min = 0;
Mirage.brightness_max = CM_ARGB_BRIGHTNESS_MAX;
Mirage.brightness = CM_ARGB_BRIGHTNESS_MAX;
Mirage.speed_min = CM_ARGB_SPEED_SLOWEST;
Mirage.speed_max = CM_ARGB_SPEED_FASTEST;
Mirage.color_mode = MODE_COLORS_MODE_SPECIFIC;
Mirage.speed = CM_ARGB_SPEED_NORMAL;
modes.push_back(Mirage);
mode PassThru;
PassThru.name = "Pass Thru";
PassThru.value = CM_RGB_MODE_PASSTHRU;
PassThru.color_mode = MODE_COLORS_NONE;
modes.push_back(PassThru);
mode Off;
Off.name = "Turn Off";
Off.value = CM_RGB_MODE_OFF;
Off.color_mode = MODE_COLORS_NONE;
modes.push_back(Off);
}
Init_Controller();
SetupZones();
int temp_mode = controller->GetMode();
for(int mode_idx = 0; mode_idx < (int)modes.size() ; mode_idx++)
/*-----------------------------------------------------*\
| Initialize the active mode to port 0 |
\*-----------------------------------------------------*/
unsigned char port_mode;
unsigned char port_speed;
unsigned char port_brightness;
bool port_random;
unsigned char port_red;
unsigned char port_green;
unsigned char port_blue;
controller->GetPortStatus(0, &port_mode, &port_speed, &port_brightness, &port_random, &port_red, &port_green, &port_blue);
for(std::size_t mode_idx = 0; mode_idx < modes.size(); mode_idx++)
{
if (temp_mode == modes[mode_idx].value)
if(modes[mode_idx].value == port_mode)
{
active_mode = mode_idx;
if((modes[mode_idx].flags & MODE_FLAG_HAS_MODE_SPECIFIC_COLOR) && (modes[mode_idx].colors.size() > 0))
{
modes[mode_idx].colors[0] = ToRGBColor(port_red, port_green, port_blue);
}
if(modes[mode_idx].flags & MODE_FLAG_HAS_SPEED)
{
modes[mode_idx].speed = port_speed;
}
if(modes[mode_idx].flags & MODE_FLAG_HAS_BRIGHTNESS)
{
modes[mode_idx].brightness = port_brightness;
}
if(modes[mode_idx].flags & MODE_FLAG_HAS_RANDOM_COLOR)
{
if(port_random)
{
modes[mode_idx].color_mode = MODE_COLORS_RANDOM;
}
}
break;
}
}
if (modes[active_mode].flags & MODE_FLAG_HAS_MODE_SPECIFIC_COLOR)
{
modes[active_mode].colors[0] = ToRGBColor(controller->GetLedRed(), controller->GetLedGreen(), controller->GetLedBlue());
modes[active_mode].color_mode = (controller->GetRandomColours()) ? MODE_COLORS_RANDOM : MODE_COLORS_MODE_SPECIFIC;
}
if (modes[active_mode].flags & MODE_FLAG_HAS_SPEED)
{
modes[active_mode].speed = controller->GetLedSpeed();
}
}
RGBController_CMARGBController::~RGBController_CMARGBController()
@@ -296,68 +248,76 @@ RGBController_CMARGBController::~RGBController_CMARGBController()
delete controller;
}
void RGBController_CMARGBController::Init_Controller()
{
int zone_idx = controller->GetZoneIndex();
int zone_led_count = argb_header_data[zone_idx].count;
/*-------------------------------------------------*\
| If argb_header_data[zone_idx].count == 1 then the |
| zone is ZONE_TYPE_SINGLE |
\*-------------------------------------------------*/
bool boolSingleLED = ( zone_led_count == 1 );
zone ARGB_zone;
ARGB_zone.name = std::to_string(zone_idx);
ARGB_zone.type = (boolSingleLED) ? ZONE_TYPE_SINGLE : ZONE_TYPE_LINEAR;
ARGB_zone.leds_min = 4;
ARGB_zone.leds_max = 48;
ARGB_zone.leds_count = zone_led_count;
ARGB_zone.matrix_map = NULL;
zones.push_back(ARGB_zone);
}
void RGBController_CMARGBController::SetupZones()
{
/*-------------------------------------------------*\
| Clear any existing color/LED configuration |
\*-------------------------------------------------*/
/*-----------------------------------------------------*\
| Only set LED count on the first run |
\*-----------------------------------------------------*/
bool first_run = false;
if(zones.size() == 0)
{
first_run = true;
}
/*-----------------------------------------------------*\
| Clear any existing color/LED configuration |
\*-----------------------------------------------------*/
leds.clear();
colors.clear();
zones.resize(5);
/*---------------------------------------------------------*\
| Set up zones |
\*---------------------------------------------------------*/
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
/*-----------------------------------------------------*\
| Set up addressable zones |
\*-----------------------------------------------------*/
for(unsigned int channel_idx = 0; channel_idx < 4; channel_idx++)
{
bool boolSingleLED = (zones[zone_idx].type == ZONE_TYPE_SINGLE);
char ch_idx_string[2];
snprintf(ch_idx_string, 2, "%d", channel_idx + 1);
if (!boolSingleLED)
zones[channel_idx].name = "Addressable RGB Header ";
zones[channel_idx].name.append(ch_idx_string);
zones[channel_idx].type = ZONE_TYPE_LINEAR;
zones[channel_idx].leds_min = 0;
zones[channel_idx].leds_max = 48;
if(first_run)
{
controller->SetLedCount( std::stoi(zones[zone_idx].name), zones[zone_idx].leds_count);
zones[channel_idx].leds_count = 0;
}
for(unsigned int lp_idx = 0; lp_idx < zones[zone_idx].leds_count; lp_idx++)
{
led new_led;
unsigned int i = std::stoi(zones[zone_idx].name);
zones[channel_idx].matrix_map = NULL;
if(boolSingleLED)
{
new_led.name = i;
new_led.value = argb_header_data[i].header;
}
else
{
new_led.name = i;
new_led.name.append(" LED " + std::to_string(lp_idx));
new_led.value = argb_header_data[i].header;
}
for(unsigned int led_ch_idx = 0; led_ch_idx < zones[channel_idx].leds_count; led_ch_idx++)
{
char led_idx_string[4];
snprintf(led_idx_string, 4, "%d", led_ch_idx + 1);
led new_led;
new_led.name = zones[channel_idx].name;
new_led.name.append(", LED ");
new_led.name.append(led_idx_string);
new_led.value = channel_idx;
leds.push_back(new_led);
}
}
/*-----------------------------------------------------*\
| Set up RGB zone |
\*-----------------------------------------------------*/
zones[4].name = "RGB Header";
zones[4].type = ZONE_TYPE_SINGLE;
zones[4].leds_min = 1;
zones[4].leds_max = 1;
zones[4].leds_count = 1;
zones[4].matrix_map = NULL;
led new_led;
new_led.name = "RGB Header";
new_led.value = 4;
leds.push_back(new_led);
SetupColors();
}
@@ -367,24 +327,20 @@ void RGBController_CMARGBController::ResizeZone(int zone, int new_size)
{
return;
}
uint8_t end_zone = last_zone(zone);
for(std::size_t zone_idx = first_zone(zone); zone_idx < end_zone; zone_idx++)
if(((unsigned int)new_size >= zones[zone].leds_min) && ((unsigned int)new_size <= zones[zone].leds_max))
{
if(((unsigned int)new_size >= zones[zone_idx].leds_min) && ((unsigned int)new_size <= zones[zone_idx].leds_max))
{
zones[zone_idx].leds_count = new_size;
}
}
zones[zone].leds_count = new_size;
SetupZones();
controller->SetPortLEDCount(zone, zones[zone].leds_count);
SetupZones();
}
}
void RGBController_CMARGBController::DeviceUpdateLEDs()
{
uint8_t end_zone = last_zone(cmargb->GetZoneIndex());
for(int zone_idx = first_zone(cmargb->GetZoneIndex()); zone_idx < end_zone; zone_idx++)
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
{
UpdateZoneLEDs(zone_idx);
}
@@ -392,37 +348,93 @@ void RGBController_CMARGBController::DeviceUpdateLEDs()
void RGBController_CMARGBController::UpdateZoneLEDs(int zone)
{
controller->SetLedsDirect( zones[zone].colors, zones[zone].leds_count );
/*-----------------------------------------------------*\
| The RGB zone doesn't have a separate Direct mode, so |
| use static mode with the per-LED color for it |
\*-----------------------------------------------------*/
if(zone < 4)
{
controller->SetPortLEDsDirect(zone, zones[zone].colors, zones[zone].leds_count);
}
else
{
controller->SetPortMode(zone, CM_RGB_MODE_STATIC, 0, 255, false, RGBGetRValue(zones[zone].colors[0]), RGBGetGValue(zones[zone].colors[0]), RGBGetBValue(zones[zone].colors[0]));
}
}
void RGBController_CMARGBController::UpdateSingleLED(int led)
{
UpdateZoneLEDs(GetLED_Zone(led));
unsigned int zone_idx = leds[led].value;
UpdateZoneLEDs(zone_idx);
}
void RGBController_CMARGBController::DeviceUpdateMode()
{
bool random_colours = (modes[active_mode].color_mode == MODE_COLORS_RANDOM);
RGBColor colour = (modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC) ? modes[active_mode].colors[0] : 0;
/*-----------------------------------------------------*\
| Determine mode parameters |
\*-----------------------------------------------------*/
bool random = (modes[active_mode].color_mode == MODE_COLORS_RANDOM);
RGBColor color = (modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC) ? modes[active_mode].colors[0] : 0;
int rgb_mode;
bool rgb_random = random;
controller->SetMode( modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, colour, random_colours );
}
int RGBController_CMARGBController::GetLED_Zone(int led_idx)
{
/*---------------------------------------------------------*\
| This may be more useful in the abstract RGBController.cpp |
\*---------------------------------------------------------*/
for(int zone_idx = 0; zone_idx < (int)zones.size(); zone_idx++)
/*-----------------------------------------------------*\
| Map ARGB modes with the equivalent RGB modes |
\*-----------------------------------------------------*/
switch(modes[active_mode].value)
{
int zone_start = zones[zone_idx].start_idx;
int zone_end = zone_start + zones[zone_idx].leds_count - 1;
case CM_ARGB_MODE_SPECTRUM:
case CM_ARGB_MODE_FILLFLOW:
case CM_ARGB_MODE_RAINBOW:
rgb_mode = CM_RGB_MODE_MIRAGE;
rgb_random = true;
break;
if(zone_start <= led_idx && zone_end >= led_idx)
{
return(zone_idx);
}
case CM_ARGB_MODE_RELOAD:
case CM_ARGB_MODE_RECOIL:
rgb_mode = CM_RGB_MODE_FLASH;
break;
case CM_ARGB_MODE_BREATHING:
rgb_mode = CM_RGB_MODE_BREATHING;
break;
case CM_ARGB_MODE_REFILL:
case CM_ARGB_MODE_STATIC:
rgb_mode = CM_RGB_MODE_STATIC;
break;
case CM_ARGB_MODE_DEMO:
rgb_mode = CM_RGB_MODE_FLASH;
rgb_random = true;
break;
case CM_ARGB_MODE_OFF:
default:
rgb_mode = CM_RGB_MODE_OFF;
break;
case CM_ARGB_MODE_PASSTHRU:
rgb_mode = CM_RGB_MODE_PASSTHRU;
break;
}
return -1;
/*-----------------------------------------------------*\
| Apply mode to all zones |
\*-----------------------------------------------------*/
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
{
controller->SetPortMode
(
zone_idx,
(zone_idx == 4) ? rgb_mode : modes[active_mode].value,
modes[active_mode].speed,
modes[active_mode].brightness,
(zone_idx == 4) ? rgb_random : random,
RGBGetRValue(color),
RGBGetGValue(color),
RGBGetBValue(color)
);
}
}
@@ -12,11 +12,8 @@
#pragma once
#include <vector>
#include "RGBController.h"
#include "CMARGBController.h"
#define first_zone(zn) ((zones.size() > 1) ? 1 : 0)
#define last_zone(zn) ((zones.size() > 1) ? 4 : 1)
#include "RGBController.h"
class RGBController_CMARGBController : public RGBController
{
@@ -34,9 +31,6 @@ public:
void DeviceUpdateMode();
private:
void Init_Controller();
int GetDeviceMode();
int GetLED_Zone(int led_idx);
CMARGBController* controller;
CMARGBController* controller;
std::vector<unsigned int> leds_channel;
};
@@ -96,19 +96,18 @@ void DetectCoolerMasterARGB(hid_device_info* info, const std::string&)
if(dev)
{
/*-------------------------------------------------*\
| Create mutex to prevent the controllers sharing a |
| receiver from interfering with each other |
\*-------------------------------------------------*/
std::shared_ptr<std::mutex> cm_mutex = std::make_shared<std::mutex>();
CMARGBController* controller = new CMARGBController(dev, info->path);
for(unsigned char i = 0; i < CM_ARGB_HEADER_DATA_SIZE; i++)
if(controller->GetVersion() != "Unsupported")
{
CMARGBController* controller = new CMARGBController(dev, info->path, i, cm_mutex);
RGBController_CMARGBController* rgb_controller = new RGBController_CMARGBController(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
}
else
{
LOG_ERROR("[CMARGBController] Unsupported firmware version");
delete controller;
}
}
}
@@ -62,6 +62,8 @@ REGISTER_HID_DETECTOR_IP("Corsair K60 RGB PRO Low Profile", DetectCorsai
REGISTER_HID_DETECTOR_IP("Corsair K60 RGB PRO TKL Black", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K60_RGB_PRO_TKL_B_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K60 RGB PRO TKL White", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K60_RGB_PRO_TKL_W_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K70 Core RGB", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K70_CORE_RGB_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K70 Core RGB TKL", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K70_CORE_RGB_TKL_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K70 RGB PRO", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K70_RGB_PRO_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K70 RGB PRO V2", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K70_RGB_PRO_V2_PID, 1, 0xFF42);
REGISTER_HID_DETECTOR_IP("Corsair K70 RGB TKL", DetectCorsairV2HardwareControllers, CORSAIR_VID, CORSAIR_K70_RGB_TKL_PID, 1, 0xFF42);
@@ -152,6 +152,28 @@ keyboard_keymap_overlay_values corsair_K70_TKL_cs_layout
}
};
keyboard_keymap_overlay_values corsair_K70_CORE_TKL_layout
{
KEYBOARD_SIZE::KEYBOARD_SIZE_TKL,
{
corsair_tkl_values,
{
/* Add more regional layout fixes here */
}
},
{
/*-------------------------------------------------------------------------------------------------------------------------------------*\
| Edit Keys |
| Zone, Row, Column, Value, Name, Alternate Name, OpCode, |
\*-------------------------------------------------------------------------------------------------------------------------------------*/
{ 0, 0, 14, 70, KEY_EN_MEDIA_MUTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Swap PRSC with Mute
{ 0, 0, 15, 71, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Remove SCLK
{ 0, 0, 16, 72, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Swap PSBK with Volume Potion Up
}
};
keyboard_keymap_overlay_values corsair_k95_layout
{
KEYBOARD_SIZE::KEYBOARD_SIZE_FULL,
@@ -929,6 +951,39 @@ static const corsair_v2_device k70_rgb_tkl_device =
&corsair_K70_TKL_cs_layout
};
/*-------------------------------------------------------------*\
| Corsair K70 Core RGB TKL 1B1C:2B01 |
| |
| Zone "Keyboard" |
| Matrix |
| 6 Rows, 1 Columns |
\*-------------------------------------------------------------*/
static const corsair_v2_zone k70_core_rgb_tkl_zone =
{
ZONE_EN_KEYBOARD,
ZONE_TYPE_MATRIX,
6,
17
};
static const corsair_v2_device k70_core_rgb_tkl_device =
{
CORSAIR_K70_CORE_RGB_TKL_PID,
DEVICE_TYPE_KEYBOARD,
6,
17,
{
&k70_core_rgb_tkl_zone,
nullptr,
nullptr,
nullptr,
nullptr,
nullptr
},
&corsair_K70_CORE_TKL_layout
};
/*-------------------------------------------------------------*\
| Corsair K70 RGB TKL Champion Series 1B1C:1BB9 |
| |
@@ -1411,6 +1466,7 @@ const corsair_v2_device* corsair_v2_device_list_data[] =
&k60_rgb_pro_tkl_device_b,
&k60_rgb_pro_tkl_device_w,
&k70_core_rgb_device,
&k70_core_rgb_tkl_device,
&k70_rgb_pro_device,
&k70_rgb_pro_v2_device,
&k70_rgb_tkl_device,
@@ -74,6 +74,7 @@ typedef struct
#define CORSAIR_K60_RGB_PRO_TKL_B_PID 0x1BC7
#define CORSAIR_K60_RGB_PRO_TKL_W_PID 0x1BED
#define CORSAIR_K70_CORE_RGB_PID 0x1BFD
#define CORSAIR_K70_CORE_RGB_TKL_PID 0x2B01
#define CORSAIR_K70_RGB_PRO_PID 0x1BC4
#define CORSAIR_K70_RGB_PRO_V2_PID 0x1BB3
#define CORSAIR_K70_RGB_TKL_PID 0x1B73
@@ -38,6 +38,8 @@ REGISTER_HID_DETECTOR("DeepRGB SIG V4F", DetectDRGBControllers, DRGBV
REGISTER_HID_DETECTOR("Airgoo AG-DRGB04", DetectDRGBControllers, DRGBV4_VID, DRGB_AG_04_V4F_PID);
REGISTER_HID_DETECTOR("Airgoo AG-DRGB16", DetectDRGBControllers, DRGBV4_VID, DRGB_AG_16_V4F_PID);
REGISTER_HID_DETECTOR("Airgoo AG-DRGB08", DetectDRGBControllers, DRGBV4_VID, DRGB_AG_08_PID);
REGISTER_HID_DETECTOR("Airgoo AG-F8-DRGB08", DetectDRGBControllers, DRGBV4_VID, DRGB_AG_08_F08_PID);
REGISTER_HID_DETECTOR("Airgoo AG-F12-DRGB16", DetectDRGBControllers, DRGBV4_VID, DRGB_AG_16_F12_PID);
REGISTER_HID_DETECTOR("DeepRGB L8 V5", DetectDRGBControllers, DRGBV4_VID, DRGB_L8_V5_PID);
@@ -93,6 +93,16 @@ void RGBController_DRGB::SetupZones()
NUM_Channel_led = 256;
Version = 4;
break;
case DRGB_AG_08_PID:
NUM_CHANNELS = 8;
NUM_Channel_led = 256;
Version = 4;
break;
case DRGB_AG_08_F08_PID:
NUM_CHANNELS = 8;
NUM_Channel_led = 256;
Version = 4;
break;
case DRGB_AG_16_V4F_PID:
NUM_CHANNELS = 16;
NUM_Channel_led = 256;
@@ -21,6 +21,8 @@
#define DRGB_SIG_V4F_PID 0x3636
#define DRGB_AG_04_V4F_PID 0x3204
#define DRGB_AG_16_V4F_PID 0x3216
#define DRGB_AG_08_PID 0x3F08
#define DRGB_AG_08_F08_PID 0x3F16
#define DRGB_AG_16_F12_PID 0x3F28
#define DRGB_L8_V5_PID 0x3208
@@ -65,7 +65,7 @@ void DygmaRaiseController::SendDirect(std::vector<RGBColor>colors, size_t led_nu
/*-----------------------------------------------------*\
| Set up led theme packet |
\*-----------------------------------------------------*/
sprintf(serial_buf,"led.theme");
snprintf(serial_buf, MAX_LEN, "led.theme");
int actual_length=9;
/*-----------------------------------------------------*\
@@ -77,20 +77,20 @@ void DygmaRaiseController::SendDirect(std::vector<RGBColor>colors, size_t led_nu
int g = RGBGetGValue(colors[led_idx]);
int b = RGBGetBValue(colors[led_idx]);
sprintf(serial_buf+actual_length," %d",r);
snprintf(serial_buf + actual_length, MAX_LEN - actual_length, " %d", r);
actual_length += val_char_len(r) + 1;
sprintf(serial_buf+actual_length," %d",g);
snprintf(serial_buf + actual_length, MAX_LEN - actual_length, " %d", g);
actual_length += val_char_len(g) + 1;
sprintf(serial_buf+actual_length," %d",b);
snprintf(serial_buf + actual_length, MAX_LEN - actual_length, " %d", b);
actual_length += val_char_len(b) + 1;
}
/*-----------------------------------------------------*\
| Add the final newline |
\*-----------------------------------------------------*/
sprintf(serial_buf+actual_length,"\n");
snprintf(serial_buf + actual_length, MAX_LEN - actual_length, "\n");
actual_length++;
/*-----------------------------------------------------*\
@@ -1,203 +0,0 @@
/*---------------------------------------------------------*\
| GigabyteRGBFusion2AorusMasterGPUController.cpp |
| |
| Driver for Gigabyte AORUS MASTER GPU with fan ring LEDs |
| |
| Protocol reverse engineered from GCC on Windows |
| Verified on Linux with i2ctransfer 2025-12-30 |
| |
| This file is part of the OpenRGB project |
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#include "GigabyteRGBFusion2AorusMasterGPUController.h"
#include "LogManager.h"
#include <chrono>
#include <thread>
RGBFusion2AorusMasterGPUController::RGBFusion2AorusMasterGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name)
{
this->bus = bus;
this->dev = dev;
this->name = dev_name;
}
RGBFusion2AorusMasterGPUController::~RGBFusion2AorusMasterGPUController()
{
}
std::string RGBFusion2AorusMasterGPUController::GetDeviceLocation()
{
std::string return_string(bus->device_name);
char addr[5];
snprintf(addr, 5, "0x%02X", dev);
return_string.append(", address ");
return_string.append(addr);
return("I2C: " + return_string);
}
std::string RGBFusion2AorusMasterGPUController::GetDeviceName()
{
return(name);
}
/*---------------------------------------------------------*\
| Send mode command to select a fan zone |
| Format: 88 01 06 63 08 <zone_id> 00 00 |
| Byte 0: Mode register (0x88) |
| Byte 1: Static mode (0x01) |
| Byte 2: Unknown constant (0x06) |
| Byte 3: Brightness (0x00-0x63) |
| Byte 4: Unknown constant (0x08) |
| Byte 5: Zone selector (0x02/0x05/0x06) |
| Byte 6-7: Padding (0x00) |
\*---------------------------------------------------------*/
void RGBFusion2AorusMasterGPUController::SendModeCommand(uint8_t zone_id, uint8_t brightness)
{
uint8_t data_pkt[8] = {
RGB_FUSION2_AORUS_MASTER_REG_MODE,
RGB_FUSION2_AORUS_MASTER_MODE_STATIC,
0x06,
brightness,
0x08,
zone_id,
0x00,
0x00
};
bus->i2c_write_block(dev, sizeof(data_pkt), data_pkt);
}
/*---------------------------------------------------------*\
| Send color to a register (controls 2 LEDs) |
| Format: <reg> <mode> R1 G1 B1 R2 G2 B2 |
| Byte 0: Register (0xB0-0xBC) |
| Byte 1: Mode byte (0x01 for fans, 0x00 for logo) |
| Byte 2-4: First LED RGB |
| Byte 5-7: Second LED RGB |
\*---------------------------------------------------------*/
void RGBFusion2AorusMasterGPUController::SendColorRegister(uint8_t reg, uint8_t mode_byte, RGBColor color1, RGBColor color2)
{
uint8_t data_pkt[8] = {
reg,
mode_byte,
(uint8_t)RGBGetRValue(color1),
(uint8_t)RGBGetGValue(color1),
(uint8_t)RGBGetBValue(color1),
(uint8_t)RGBGetRValue(color2),
(uint8_t)RGBGetGValue(color2),
(uint8_t)RGBGetBValue(color2)
};
bus->i2c_write_block(dev, sizeof(data_pkt), data_pkt);
}
/*---------------------------------------------------------*\
| Set colors for a fan zone (8 LEDs = 4 registers) |
| Must send mode command before color commands |
| |
| fan_index: 0=left, 1=middle, 2=right |
| colors: Array of 8 RGB colors for the 8 LEDs |
\*---------------------------------------------------------*/
void RGBFusion2AorusMasterGPUController::SetFanColors(uint8_t fan_index, RGBColor colors[8], uint8_t brightness)
{
uint8_t zone_id;
uint8_t base_reg;
switch(fan_index)
{
case 0:
zone_id = RGB_FUSION2_AORUS_MASTER_ZONE_LEFT;
base_reg = RGB_FUSION2_AORUS_MASTER_REG_LEFT_FAN;
break;
case 1:
zone_id = RGB_FUSION2_AORUS_MASTER_ZONE_MIDDLE;
base_reg = RGB_FUSION2_AORUS_MASTER_REG_MIDDLE_FAN;
break;
case 2:
zone_id = RGB_FUSION2_AORUS_MASTER_ZONE_RIGHT;
base_reg = RGB_FUSION2_AORUS_MASTER_REG_RIGHT_FAN;
break;
default:
LOG_ERROR("[%s] Invalid fan index: %d", name.c_str(), fan_index);
return;
}
/*---------------------------------------------------------*\
| CRITICAL: Send mode command with zone ID first |
| Without this, color commands have no effect |
\*---------------------------------------------------------*/
SendModeCommand(zone_id, brightness);
/*---------------------------------------------------------*\
| Delay after mode command - firmware needs time to process |
| the zone selection before accepting color data |
\*---------------------------------------------------------*/
std::this_thread::sleep_for(std::chrono::milliseconds(5));
/*---------------------------------------------------------*\
| Send 4 color registers (2 LEDs each) |
| Register Bx+0: LEDs 0,1 (colors[0], colors[1]) |
| Register Bx+1: LEDs 2,3 (colors[2], colors[3]) |
| Register Bx+2: LEDs 4,5 (colors[4], colors[5]) |
| Register Bx+3: LEDs 6,7 (colors[6], colors[7]) |
\*---------------------------------------------------------*/
for(int reg_offset = 0; reg_offset < 4; reg_offset++)
{
uint8_t reg = base_reg + reg_offset;
int color_idx = reg_offset * 2;
SendColorRegister(reg, 0x01, colors[color_idx], colors[color_idx + 1]);
std::this_thread::sleep_for(std::chrono::milliseconds(1));
}
/*---------------------------------------------------------*\
| Apply after each zone - required for multi-zone update |
\*---------------------------------------------------------*/
ApplyChanges();
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}
/*---------------------------------------------------------*\
| Set logo color |
| Format: BC 00 R G B 00 00 00 |
| Note: Logo uses mode byte 0x00, not 0x01 |
\*---------------------------------------------------------*/
void RGBFusion2AorusMasterGPUController::SetLogoColor(RGBColor color)
{
uint8_t data_pkt[8] = {
RGB_FUSION2_AORUS_MASTER_REG_LOGO,
0x00,
(uint8_t)RGBGetRValue(color),
(uint8_t)RGBGetGValue(color),
(uint8_t)RGBGetBValue(color),
0x00,
0x00,
0x00
};
bus->i2c_write_block(dev, sizeof(data_pkt), data_pkt);
}
/*---------------------------------------------------------*\
| Apply all pending changes |
| Format: AA 00 00 00 00 00 00 00 |
\*---------------------------------------------------------*/
void RGBFusion2AorusMasterGPUController::ApplyChanges()
{
uint8_t data_pkt[8] = {
RGB_FUSION2_AORUS_MASTER_REG_APPLY,
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
0x00
};
bus->i2c_write_block(dev, sizeof(data_pkt), data_pkt);
}
@@ -1,97 +0,0 @@
/*---------------------------------------------------------*\
| GigabyteRGBFusion2AorusMasterGPUController.h |
| |
| Driver for Gigabyte AORUS MASTER GPU with fan ring LEDs |
| |
| Protocol reverse engineered from GCC on Windows |
| Fan LEDs only illuminate when fans are spinning |
| |
| This file is part of the OpenRGB project |
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#pragma once
#include <string>
#include "i2c_smbus.h"
#include "RGBController.h"
typedef unsigned char rgb_fusion_dev_id;
/*---------------------------------------------------------*\
| Fan zone configuration |
| Each fan has 8 LEDs controlled by 4 registers |
| Each register controls 2 LEDs with dual RGB values |
\*---------------------------------------------------------*/
struct aorus_master_zone_colors
{
RGBColor led_colors[8]; // 8 LEDs per fan (or 1 for logo)
};
/*---------------------------------------------------------*\
| Register definitions |
\*---------------------------------------------------------*/
enum
{
RGB_FUSION2_AORUS_MASTER_REG_MODE = 0x88,
RGB_FUSION2_AORUS_MASTER_REG_APPLY = 0xAA,
RGB_FUSION2_AORUS_MASTER_REG_LEFT_FAN = 0xB0, // B0-B3
RGB_FUSION2_AORUS_MASTER_REG_MIDDLE_FAN = 0xB4, // B4-B7
RGB_FUSION2_AORUS_MASTER_REG_RIGHT_FAN = 0xB8, // B8-BB
RGB_FUSION2_AORUS_MASTER_REG_LOGO = 0xBC,
};
/*---------------------------------------------------------*\
| Fan zone ID values for mode command (byte 5) |
\*---------------------------------------------------------*/
enum
{
RGB_FUSION2_AORUS_MASTER_ZONE_LEFT = 0x02, // IO side fan
RGB_FUSION2_AORUS_MASTER_ZONE_MIDDLE = 0x05, // Center fan
RGB_FUSION2_AORUS_MASTER_ZONE_RIGHT = 0x06, // Far side fan
};
/*---------------------------------------------------------*\
| Mode definitions |
\*---------------------------------------------------------*/
enum
{
RGB_FUSION2_AORUS_MASTER_MODE_STATIC = 0x01,
};
/*---------------------------------------------------------*\
| Speed and brightness |
\*---------------------------------------------------------*/
enum
{
RGB_FUSION2_AORUS_MASTER_BRIGHTNESS_MIN = 0x00,
RGB_FUSION2_AORUS_MASTER_BRIGHTNESS_MAX = 0x63, // 99
};
/*---------------------------------------------------------*\
| Zone count: 3 fans x 8 LEDs + 1 logo = 25 zones |
\*---------------------------------------------------------*/
#define RGB_FUSION_2_AORUS_MASTER_FAN_LEDS 8
#define RGB_FUSION_2_AORUS_MASTER_TOTAL_ZONES 25
class RGBFusion2AorusMasterGPUController
{
public:
RGBFusion2AorusMasterGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name);
~RGBFusion2AorusMasterGPUController();
std::string GetDeviceLocation();
std::string GetDeviceName();
void SetFanColors(uint8_t fan_index, RGBColor colors[8], uint8_t brightness);
void SetLogoColor(RGBColor color);
void ApplyChanges();
private:
i2c_smbus_interface* bus;
rgb_fusion_dev_id dev;
std::string name;
void SendModeCommand(uint8_t zone_id, uint8_t brightness);
void SendColorRegister(uint8_t reg, uint8_t mode_byte, RGBColor color1, RGBColor color2);
};
@@ -1,82 +0,0 @@
/*---------------------------------------------------------*\
| GigabyteRGBFusion2AorusMasterGPUControllerDetect.cpp |
| |
| Detector for Gigabyte AORUS MASTER GPU |
| |
| This file is part of the OpenRGB project |
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#include <stdio.h>
#include "Detector.h"
#include "GigabyteRGBFusion2AorusMasterGPUController.h"
#include "i2c_smbus.h"
#include "LogManager.h"
#include "pci_ids.h"
#include "RGBController_GigabyteRGBFusion2AorusMasterGPU.h"
#define GIGABYTEGPU_CONTROLLER_NAME_AORUS_MASTER "Gigabyte RGB Fusion2 AORUS MASTER GPU"
bool TestForGigabyteRGBFusion2AorusMasterGPUController(i2c_smbus_interface* bus, unsigned char address)
{
bool pass = false;
int res, pktsz;
const int read_sz = 4;
const int write_sz = 8;
uint8_t data_pkt[write_sz] = { 0xAB, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
uint8_t data_readpkt[read_sz] = {};
res = bus->i2c_write_block(address, write_sz, data_pkt);
if(res < 0)
{
LOG_DEBUG("[%s] Write probe failed at address 0x%02X", GIGABYTEGPU_CONTROLLER_NAME_AORUS_MASTER, address);
return false;
}
pktsz = read_sz;
res = bus->i2c_read_block(address, &pktsz, data_readpkt);
/*-----------------------------------------------------*\
| All RGB Fusion 2 responses start with 0xAB |
| RTX 5080 AORUS MASTER response: 0xAB 0x10 0x52 0x0B |
\*-----------------------------------------------------*/
if(res >= 0 && data_readpkt[0] == 0xAB)
{
pass = true;
LOG_DEBUG("[%s] Detected at address 0x%02X with response: 0x%02X 0x%02X 0x%02X 0x%02X",
GIGABYTEGPU_CONTROLLER_NAME_AORUS_MASTER, address,
data_readpkt[0], data_readpkt[1], data_readpkt[2], data_readpkt[3]);
}
else
{
std::string text = "";
for(int idx = 0; idx < read_sz; ++idx)
{
char str[6];
snprintf(str, 6, " 0x%02X", data_readpkt[idx]);
text.append(str);
}
LOG_DEBUG("[%s] at address 0x%02X invalid. Expected 0xAB [0x*] but received:%s",
GIGABYTEGPU_CONTROLLER_NAME_AORUS_MASTER, address, text.c_str());
}
return(pass);
}
void DetectGigabyteRGBFusion2AorusMasterGPUControllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
{
if(TestForGigabyteRGBFusion2AorusMasterGPUController(bus, i2c_addr))
{
RGBFusion2AorusMasterGPUController* controller = new RGBFusion2AorusMasterGPUController(bus, i2c_addr, name);
RGBController_RGBFusion2AorusMasterGPU* rgb_controller = new RGBController_RGBFusion2AorusMasterGPU(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
}
}
/*---------------------------------------------------------*\
| Nvidia GPUs |
\*---------------------------------------------------------*/
REGISTER_I2C_PCI_DETECTOR("Gigabyte AORUS GeForce RTX 5080 MASTER", DetectGigabyteRGBFusion2AorusMasterGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_AORUS_RTX5080_MASTER_16G_SUB_DEV, 0x71);
@@ -1,180 +0,0 @@
/*---------------------------------------------------------*\
| RGBController_GigabyteRGBFusion2AorusMasterGPU.cpp |
| |
| RGBController for Gigabyte AORUS MASTER GPU |
| |
| Each fan has 8 individually addressable LEDs |
| Plus 1 logo LED = 25 total LEDs |
| |
| Note: Fan LEDs only illuminate when fans are spinning |
| Use nvidia-settings to force fans on for testing |
| |
| This file is part of the OpenRGB project |
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#include "RGBController_GigabyteRGBFusion2AorusMasterGPU.h"
#include "LogManager.h"
/**------------------------------------------------------------------*\
@name Gigabyte AORUS MASTER GPU
@category GPU
@type I2C
@save :white_check_mark:
@direct :white_check_mark:
@effects :x:
@detectors DetectGigabyteRGBFusion2AorusMasterGPUControllers
@comment Fan LEDs only work when fans are spinning. Each fan has 8
individually addressable LEDs. Protocol uses zone-based
mode commands before color commands.
\*-------------------------------------------------------------------*/
RGBController_RGBFusion2AorusMasterGPU::RGBController_RGBFusion2AorusMasterGPU(RGBFusion2AorusMasterGPUController* controller_ptr)
{
controller = controller_ptr;
name = controller->GetDeviceName();
vendor = "Gigabyte";
description = "Gigabyte AORUS MASTER GPU with Fan Ring LEDs";
location = controller->GetDeviceLocation();
type = DEVICE_TYPE_GPU;
mode Direct;
Direct.name = "Direct";
Direct.value = RGB_FUSION2_AORUS_MASTER_MODE_STATIC;
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_MANUAL_SAVE;
Direct.color_mode = MODE_COLORS_PER_LED;
Direct.brightness_min = RGB_FUSION2_AORUS_MASTER_BRIGHTNESS_MIN;
Direct.brightness_max = RGB_FUSION2_AORUS_MASTER_BRIGHTNESS_MAX;
Direct.brightness = RGB_FUSION2_AORUS_MASTER_BRIGHTNESS_MAX;
modes.push_back(Direct);
SetupZones();
}
RGBController_RGBFusion2AorusMasterGPU::~RGBController_RGBFusion2AorusMasterGPU()
{
delete controller;
}
void RGBController_RGBFusion2AorusMasterGPU::SetupZones()
{
/*---------------------------------------------------------*\
| Create 3 fan zones with 8 LEDs each (linear zones) |
\*---------------------------------------------------------*/
const char* fan_names[] = { "Left Fan", "Middle Fan", "Right Fan" };
for(int fan_idx = 0; fan_idx < 3; fan_idx++)
{
zone fan_zone;
fan_zone.name = fan_names[fan_idx];
fan_zone.type = ZONE_TYPE_LINEAR;
fan_zone.leds_min = 8;
fan_zone.leds_max = 8;
fan_zone.leds_count = 8;
fan_zone.matrix_map = NULL;
zones.push_back(fan_zone);
/*-----------------------------------------------------*\
| Create 8 LEDs for this fan zone |
\*-----------------------------------------------------*/
for(int led_idx = 0; led_idx < 8; led_idx++)
{
led new_led;
new_led.name = fan_names[fan_idx];
new_led.name.append(" LED ");
new_led.name.append(std::to_string(led_idx + 1));
leds.push_back(new_led);
}
}
/*---------------------------------------------------------*\
| Create logo zone with 1 LED |
\*---------------------------------------------------------*/
zone logo_zone;
logo_zone.name = "Logo";
logo_zone.type = ZONE_TYPE_SINGLE;
logo_zone.leds_min = 1;
logo_zone.leds_max = 1;
logo_zone.leds_count = 1;
logo_zone.matrix_map = NULL;
zones.push_back(logo_zone);
led logo_led;
logo_led.name = "Logo";
leds.push_back(logo_led);
SetupColors();
}
void RGBController_RGBFusion2AorusMasterGPU::ResizeZone(int /*zone*/, int /*new_size*/)
{
/*---------------------------------------------------------*\
| This device does not support resizing zones |
\*---------------------------------------------------------*/
}
void RGBController_RGBFusion2AorusMasterGPU::DeviceUpdateLEDs()
{
uint8_t brightness = modes[active_mode].brightness;
/*---------------------------------------------------------*\
| Update each fan zone |
| LED indices: 0-7 (left), 8-15 (middle), 16-23 (right) |
\*---------------------------------------------------------*/
for(int fan_idx = 0; fan_idx < 3; fan_idx++)
{
RGBColor fan_colors[8];
int base_led_idx = fan_idx * 8;
for(int led_idx = 0; led_idx < 8; led_idx++)
{
fan_colors[led_idx] = colors[base_led_idx + led_idx];
}
controller->SetFanColors(fan_idx, fan_colors, brightness);
}
/*---------------------------------------------------------*\
| Update logo (LED index 24) |
\*---------------------------------------------------------*/
controller->SetLogoColor(colors[24]);
/*---------------------------------------------------------*\
| Apply all changes |
\*---------------------------------------------------------*/
controller->ApplyChanges();
}
void RGBController_RGBFusion2AorusMasterGPU::UpdateZoneLEDs(int /*zone*/)
{
/*---------------------------------------------------------*\
| For simplicity, update all LEDs when any zone changes |
| The protocol requires sequential updates anyway |
\*---------------------------------------------------------*/
DeviceUpdateLEDs();
}
void RGBController_RGBFusion2AorusMasterGPU::UpdateSingleLED(int /*led*/)
{
/*---------------------------------------------------------*\
| For simplicity, update all LEDs when any LED changes |
| The protocol requires mode command + color sequence |
\*---------------------------------------------------------*/
DeviceUpdateLEDs();
}
void RGBController_RGBFusion2AorusMasterGPU::DeviceUpdateMode()
{
DeviceUpdateLEDs();
}
void RGBController_RGBFusion2AorusMasterGPU::DeviceSaveMode()
{
/*---------------------------------------------------------*\
| Apply command also saves to device memory |
\*---------------------------------------------------------*/
controller->ApplyChanges();
}
@@ -1,34 +0,0 @@
/*---------------------------------------------------------*\
| RGBController_GigabyteRGBFusion2AorusMasterGPU.h |
| |
| RGBController for Gigabyte AORUS MASTER GPU |
| |
| This file is part of the OpenRGB project |
| SPDX-License-Identifier: GPL-2.0-or-later |
\*---------------------------------------------------------*/
#pragma once
#include "RGBController.h"
#include "GigabyteRGBFusion2AorusMasterGPUController.h"
class RGBController_RGBFusion2AorusMasterGPU : public RGBController
{
public:
RGBController_RGBFusion2AorusMasterGPU(RGBFusion2AorusMasterGPUController* controller_ptr);
~RGBController_RGBFusion2AorusMasterGPU();
void SetupZones();
void ResizeZone(int zone, int new_size);
void DeviceUpdateLEDs();
void UpdateZoneLEDs(int zone);
void UpdateSingleLED(int led);
void DeviceUpdateMode();
void DeviceSaveMode();
private:
RGBFusion2AorusMasterGPUController* controller;
};
@@ -15,11 +15,12 @@
using namespace std::chrono_literals;
RGBFusion2BlackwellGPUController::RGBFusion2BlackwellGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name)
RGBFusion2BlackwellGPUController::RGBFusion2BlackwellGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name, int gpu_layout)
{
this->bus = bus;
this->dev = dev;
this->name = dev_name;
this->bus = bus;
this->dev = dev;
this->name = dev_name;
this->gpu_layout = gpu_layout;
}
RGBFusion2BlackwellGPUController::~RGBFusion2BlackwellGPUController()
@@ -51,7 +52,7 @@ void RGBFusion2BlackwellGPUController::SaveConfig()
void RGBFusion2BlackwellGPUController::SetMode(uint8_t type, uint8_t zone, uint8_t mode, fusion2_config zone_config)
{
if(zone_config.numberOfColors == 0 && zone < RGB_FUSION_2_BLACKWELL_GPU_NUMBER_OF_ZONES)
this->zone_color[zone] = zone_config.colors[zone];
this->zone_color[zone] = zone_config.colors[0];
/************************************************************************************\
* *
@@ -67,6 +68,11 @@ void RGBFusion2BlackwellGPUController::SetMode(uint8_t type, uint8_t zone, uint8
if(zone_config.numberOfColors > 0)
{
int currentPos = 12;
if(gpu_layout == RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT)
{
currentPos = 11;
}
for(uint8_t i = 0; i < zone_config.numberOfColors; i++)
{
zone_pkt[currentPos + 0] = RGBGetRValue(zone_config.colors[i]);
@@ -44,6 +44,7 @@ enum
RGB_FUSION2_BLACKWELL_GPU_MODE_COLOR_SHIFT = 0x08, // Not available to Eagle/Aero
RGB_FUSION2_BLACKWELL_GPU_MODE_TRICOLOR = 0x09, // Available to Waterforce
RGB_FUSION2_BLACKWELL_GPU_MODE_DAZZLE = 0x0A, // Not available to Eagle/Aero/Waterforce
RGB_FUSION2_BLACKWELL_GPU_MODE_CLAWS = 0x0C, // Available to AORUS 5080 MASTER
};
enum
@@ -61,16 +62,17 @@ enum
enum
{
RGB_FUSION2_BLACKWELL_GPU_SINGLE_ZONE = 0,
RGB_FUSION2_BLACKWELL_GPU_GAMING_LAYOUT = 1,
RGB_FUSION2_BLACKWELL_GPU_WATERFORCE_LAYOUT = 2,
RGB_FUSION2_BLACKWELL_GPU_AORUS_WATERFORCE_LAYOUT = 3,
RGB_FUSION2_BLACKWELL_GPU_SINGLE_ZONE = 0,
RGB_FUSION2_BLACKWELL_GPU_GAMING_LAYOUT = 1,
RGB_FUSION2_BLACKWELL_GPU_WATERFORCE_LAYOUT = 2,
RGB_FUSION2_BLACKWELL_GPU_AORUS_WATERFORCE_LAYOUT = 3,
RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT = 4,
};
class RGBFusion2BlackwellGPUController
{
public:
RGBFusion2BlackwellGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name);
RGBFusion2BlackwellGPUController(i2c_smbus_interface* bus, rgb_fusion_dev_id dev, std::string dev_name, int gpu_layout);
~RGBFusion2BlackwellGPUController();
RGBColor zone_color[RGB_FUSION_2_BLACKWELL_GPU_NUMBER_OF_ZONES];
@@ -87,4 +89,6 @@ private:
i2c_smbus_interface* bus;
rgb_fusion_dev_id dev;
std::string name;
int gpu_layout;
};
@@ -52,6 +52,7 @@ bool TestForGigabyteRGBFusion2BlackwellGPUController(i2c_smbus_interface* bus, u
//GeForce RTX 5070 Ti Eagle OC 16G 0x01 0x01 0x01 0x00
//GeForce RTX 5070 Ti Gaming OC 16G 0x01 0x01 0x01 0x00
//GeForce RTX 5070 Gaming OC 12G 0x01 0x01 0x01 0x00
//GeForce RTX 5080 AORUS MASTER 16G 0x01 0x01 0x01 0x10
if(res < 0 || data_readpkt[0] != 0x01 || data_readpkt[1] != 0x01 || data_readpkt[2] != 0x01)
{
@@ -89,7 +90,7 @@ void DetectGigabyteRGBFusion2BlackwellGPUControllers(i2c_smbus_interface* bus, u
// Check for RGB Fusion2 controller
if(TestForGigabyteRGBFusion2BlackwellGPUController(bus, i2c_addr))
{
RGBFusion2BlackwellGPUController* controller = new RGBFusion2BlackwellGPUController(bus, i2c_addr, name);
RGBFusion2BlackwellGPUController* controller = new RGBFusion2BlackwellGPUController(bus, i2c_addr, name, led_zones);
RGBController_RGBFusion2BlackwellGPU* rgb_controller = new RGBController_RGBFusion2BlackwellGPU(controller, led_zones);
ResourceManager::get()->RegisterRGBController(rgb_controller);
@@ -163,6 +164,24 @@ void DetectGigabyteRGBFusion2BlackwellAorusWaterforceLayoutGPUControllers(i2c_sm
DetectGigabyteRGBFusion2BlackwellGPUControllers(bus, i2c_addr, name, RGB_FUSION2_BLACKWELL_GPU_AORUS_WATERFORCE_LAYOUT);
} /* DetectGigabyteRGBFusion2BlackwellAorusWaterforceLayoutGPUControllers() */
/*******************************************************************************************\
* *
* DetectGigabyteRGBFusion2BlackwellAorusMaster5080LayoutGPUControllers *
* *
* Detect GigabyteRGB Fusion2 controllers with AORUS waterforce layout on the *
* enumerated I2C busses. *
* *
* bus - pointer to i2c_smbus_interface where RGB Fusion2 device is connected *
* dev - I2C address of RGB Fusion2 device *
* *
\*******************************************************************************************/
void DetectGigabyteRGBFusion2BlackwellAorusMaster5080LayoutGPUControllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
{
DetectGigabyteRGBFusion2BlackwellGPUControllers(bus, i2c_addr, name, RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT);
} /* DetectGigabyteRGBFusion2BlackwellAorusMaster5080LayoutGPUControllers() */
/*-----------------------------------------*\
| Nvidia GPUs |
\*-----------------------------------------*/
@@ -177,6 +196,7 @@ REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5070 Ti Aero OC",
REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5070 Ti Gaming OC", DetectGigabyteRGBFusion2BlackwellGamingLayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, GIGABYTE_SUB_VEN, GIGABYTE_RTX5070TI_GAMING_OC_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5080 Aero OC", DetectGigabyteRGBFusion2BlackwellSingleZoneGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_RTX5080_AERO_OC_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5080 Gaming OC", DetectGigabyteRGBFusion2BlackwellGamingLayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_RTX5080_GAMING_OC_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte AORUS GeForce RTX 5080 MASTER", DetectGigabyteRGBFusion2BlackwellAorusMaster5080LayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_AORUS_RTX5080_MASTER_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte AORUS GeForce RTX 5080 XTREME WATERFORCE", DetectGigabyteRGBFusion2BlackwellAorusWaterforceLayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_AORUS_RTX5080_XTREME_WATERFORCE_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5080 XTREME WATERFORCE", DetectGigabyteRGBFusion2BlackwellWaterforceLayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, GIGABYTE_SUB_VEN, GIGABYTE_RTX5080_XTREME_WATERFORCE_16G_SUB_DEV, 0x75);
REGISTER_I2C_PCI_DETECTOR("Gigabyte GeForce RTX 5090 Gaming OC", DetectGigabyteRGBFusion2BlackwellGamingLayoutGPUControllers, NVIDIA_VEN, NVIDIA_RTX5090_DEV, GIGABYTE_SUB_VEN, GIGABYTE_RTX5090_GAMING_OC_32G_SUB_DEV, 0x75);
@@ -10,3 +10,4 @@
#pragma once
#define RGB_FUSION_2_BLACKWELL_GPU_NUMBER_OF_ZONES 6
#define RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS 8
@@ -106,7 +106,7 @@ RGBController_RGBFusion2BlackwellGPU::RGBController_RGBFusion2BlackwellGPU(RGBFu
SpectrumCycle.brightness = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
modes.push_back(SpectrumCycle);
if(led_layout == RGB_FUSION2_BLACKWELL_GPU_GAMING_LAYOUT || led_layout == RGB_FUSION2_BLACKWELL_GPU_WATERFORCE_LAYOUT || led_layout == RGB_FUSION2_BLACKWELL_GPU_AORUS_WATERFORCE_LAYOUT)
if(led_layout != RGB_FUSION2_BLACKWELL_GPU_SINGLE_ZONE)
{
mode Wave;
Wave.name = "Wave";
@@ -150,26 +150,53 @@ RGBController_RGBFusion2BlackwellGPU::RGBController_RGBFusion2BlackwellGPU(RGBFu
ColorShift.brightness = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
modes.push_back(ColorShift);
/* Disabled Dazzle as it seems to only execute once, would need to loop it maybe?
* Not for Waterforce
mode Dazzle;
Dazzle.name = "Dazzle";
Dazzle.value = RGB_FUSION2_BLACKWELL_GPU_MODE_DAZZLE;
Dazzle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_MANUAL_SAVE;
Dazzle.speed_min = RGB_FUSION2_BLACKWELL_GPU_SPEED_SLOWEST;
Dazzle.speed_max = RGB_FUSION2_BLACKWELL_GPU_SPEED_FASTEST;
Dazzle.speed = RGB_FUSION2_BLACKWELL_GPU_SPEED_NORMAL;
Dazzle.color_mode = MODE_COLORS_MODE_SPECIFIC;
Dazzle.colors_min = 1;
Dazzle.colors_max = 8;
Dazzle.colors.resize(8);
Dazzle.brightness_min = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MIN;
Dazzle.brightness_max = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
Dazzle.brightness = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
modes.push_back(Dazzle);*/
if(led_layout != RGB_FUSION2_BLACKWELL_GPU_AORUS_WATERFORCE_LAYOUT)
{
mode Dazzle;
Dazzle.name = "Dazzle";
Dazzle.value = RGB_FUSION2_BLACKWELL_GPU_MODE_DAZZLE;
Dazzle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_MANUAL_SAVE;
Dazzle.speed_min = RGB_FUSION2_BLACKWELL_GPU_SPEED_SLOWEST;
Dazzle.speed_max = RGB_FUSION2_BLACKWELL_GPU_SPEED_FASTEST;
Dazzle.speed = RGB_FUSION2_BLACKWELL_GPU_SPEED_NORMAL;
Dazzle.color_mode = MODE_COLORS_MODE_SPECIFIC;
Dazzle.colors_min = 1;
Dazzle.colors_max = 8;
Dazzle.colors.resize(8);
Dazzle.brightness_min = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MIN;
Dazzle.brightness_max = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
Dazzle.brightness = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
modes.push_back(Dazzle);
}
}
SetupZones();
if(led_layout == RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT)
{
mode Claws;
Claws.name = "Claws";
Claws.value = RGB_FUSION2_BLACKWELL_GPU_MODE_CLAWS;
Claws.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_MANUAL_SAVE;
Claws.speed_min = RGB_FUSION2_BLACKWELL_GPU_SPEED_SLOWEST;
Claws.speed_max = RGB_FUSION2_BLACKWELL_GPU_SPEED_FASTEST;
Claws.speed = RGB_FUSION2_BLACKWELL_GPU_SPEED_NORMAL;
Claws.color_mode = MODE_COLORS_MODE_SPECIFIC;
Claws.brightness_min = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MIN;
Claws.brightness_max = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
Claws.brightness = RGB_FUSION2_BLACKWELL_GPU_BRIGHTNESS_MAX;
modes.push_back(Claws);
for(size_t i = 0; i < modes.size(); i++)
{
if(modes[i].color_mode == MODE_COLORS_PER_LED)
{
modes[i].colors_min = 1;
modes[i].colors_max = RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS;
modes[i].colors.resize(RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS);
}
}
}
RGBController_RGBFusion2BlackwellGPU::SetupZones();
}
RGBController_RGBFusion2BlackwellGPU::~RGBController_RGBFusion2BlackwellGPU()
@@ -322,6 +349,56 @@ void RGBController_RGBFusion2BlackwellGPU::SetupZones()
zones.push_back(new_zone);
}
}
else if(gpu_layout == RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT)
{
const char * fan_names[] = { "Right Fan", "Left Fan", "Middle Fan" };
for(int i = 0; i < 3; i++)
{
zone fan_zone;
fan_zone.name = fan_names[i];
fan_zone.type = ZONE_TYPE_LINEAR;
fan_zone.leds_min = RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS;
fan_zone.leds_max = RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS;
fan_zone.leds_count = RGB_FUSION_2_BLACKWELL_AORUS_MASTER_FAN_LEDS;
fan_zone.matrix_map = NULL;
zones.push_back(fan_zone);
for(unsigned int led_idx = 0; led_idx < fan_zone.leds_count; led_idx++)
{
led new_led;
new_led.name = fan_names[i];
new_led.name.append(" LED ");
new_led.name.append(std::to_string(led_idx + 1));
leds.push_back(new_led);
}
}
zone side_logo;
side_logo.name = "Side Logo";
side_logo.type = ZONE_TYPE_SINGLE;
side_logo.leds_min = 1;
side_logo.leds_max = 1;
side_logo.leds_count = 1;
side_logo.matrix_map = NULL;
zones.push_back(side_logo);
led logo_led;
logo_led.name = "Side Logo";
leds.push_back(logo_led);
zone top_logo;
top_logo.name = "Top Logo";
top_logo.type = ZONE_TYPE_SINGLE;
top_logo.leds_min = 1;
top_logo.leds_max = 1;
top_logo.leds_count = 1;
top_logo.matrix_map = NULL;
zones.push_back(top_logo);
led top_led;
top_led.name = "Top Logo";
leds.push_back(top_led);
}
SetupColors();
}
@@ -336,7 +413,6 @@ void RGBController_RGBFusion2BlackwellGPU::ResizeZone(int /*zone*/, int /*new_si
void RGBController_RGBFusion2BlackwellGPU::DeviceUpdateLEDs()
{
fusion2_config zone_config;
zone_config.brightness = modes[active_mode].brightness;
zone_config.speed = modes[active_mode].speed;
zone_config.direction = modes[active_mode].direction;
@@ -366,6 +442,10 @@ void RGBController_RGBFusion2BlackwellGPU::DeviceUpdateLEDs()
gpu_zones = 5; // Hardware zones 0-4, but zone 0 is skipped
break;
case RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT:
gpu_zones = 6; // Zones 4 and 5 refer to ui zone 4
break;
default:
LOG_TRACE("[%s] Invalid GPU layout (%d) when updating LEDs.", name.c_str(), gpu_layout);
return; // should not happen
@@ -392,19 +472,51 @@ void RGBController_RGBFusion2BlackwellGPU::DeviceUpdateLEDs()
}
ui_zone_idx = zone_idx - 1; // Map: HW zone 1->UI zone 0, HW zone 2->UI zone 1, HW zone 3->UI zone 2, HW zone 4->UI zone 3
}
else if(gpu_layout == RGB_FUSION2_BLACKWELL_GPU_AORUS_MASTER_5080_LAYOUT)
{
if(zone_idx == 5)
{
ui_zone_idx = zone_idx - 1; // Map: HW zone 5->UI zone 4
}
}
if(ui_zone_idx >= zones.size())
{
zone_config.colors[hardware_zone_idx] = colors.back();
zone_config.colors[0] = colors.back();
}
else
{
zone_config.colors[hardware_zone_idx] = colors[ui_zone_idx];
/*---------------------------------------------------------*\
| Equivalent of: |
| zone_config.colors[0] = colors[ui_zone_idx]; |
| when all zones have 1 led. |
\*---------------------------------------------------------*/
uint8_t led_start = 0;
for(uint8_t i = 0; i < ui_zone_idx; i++)
{
led_start += zones[i].leds_count;
}
for(unsigned int i = 0; i < zones[ui_zone_idx].leds_count; i++)
{
zone_config.colors[i] = colors[led_start + i];
}
/*---------------------------------------------------------*\
| If not all led are the same color, then we must pass all |
| led colors in the i2c write. |
\*---------------------------------------------------------*/
if(!std::all_of(zone_config.colors, zone_config.colors + zones[ui_zone_idx].leds_count, [first = zone_config.colors[0]](RGBColor x) { return x == first; }))
{
zone_config.numberOfColors = zones[ui_zone_idx].leds_count;
}
}
for(uint8_t i = 0; i < zone_config.numberOfColors; i++) // specific for MODE_COLORS_MODE_SPECIFIC
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
{
zone_config.colors[i] = modes[active_mode].colors[i];
for(uint8_t i = 0; i < zone_config.numberOfColors; i++) // specific for MODE_COLORS_MODE_SPECIFIC
{
zone_config.colors[i] = modes[active_mode].colors[i];
}
}
controller->SetZone(hardware_zone_idx, modes[active_mode].value, zone_config);
@@ -91,7 +91,7 @@ void RGBController_HPOmenLaptopWMI_Windows::SetupZones()
SetupColors();
}
void RGBController_HPOmenLaptopWMI_Windows::ResizeZone(int zone, int new_size)
void RGBController_HPOmenLaptopWMI_Windows::ResizeZone(int /*zone*/, int /*new_size*/)
{
/*-----------------------------------------------------*\
| Not Supported |
@@ -106,7 +106,7 @@ void RGBController_HPOmenLaptopWMI_Windows::DeviceUpdateLEDs()
controller->setColors(this->colors);
}
void RGBController_HPOmenLaptopWMI_Windows::UpdateZoneLEDs(int zone)
void RGBController_HPOmenLaptopWMI_Windows::UpdateZoneLEDs(int /*zone*/)
{
/*-----------------------------------------------------*\
| Set new colors |
@@ -114,7 +114,7 @@ void RGBController_HPOmenLaptopWMI_Windows::UpdateZoneLEDs(int zone)
controller->setColors(this->colors);
}
void RGBController_HPOmenLaptopWMI_Windows::UpdateSingleLED(int led)
void RGBController_HPOmenLaptopWMI_Windows::UpdateSingleLED(int /*led*/)
{
/*-----------------------------------------------------*\
| Set new colors |
@@ -18,7 +18,7 @@
#include "ResourceManager.h"
#include "SettingsManager.h"
#include "JGINYUEInternalUSBV2Controller.h"
#include "LogManager.h"
#include "dmiinfo.h"
#define JGINYUE_V2_HID_GENERAL_COMMAND_HEADER 0x01
@@ -55,8 +55,10 @@ JGINYUEInternalUSBV2Controller::JGINYUEInternalUSBV2Controller(hid_device* jy_hi
JGINYUEInternalUSBV2Controller::~JGINYUEInternalUSBV2Controller()
{
hid_close(jy_hid_interface);
delete jy_cdc_interface;
if(jy_cdc_interface != nullptr)
{
delete jy_cdc_interface;
}
}
unsigned int JGINYUEInternalUSBV2Controller::GetZoneCount()
@@ -91,14 +93,26 @@ void JGINYUEInternalUSBV2Controller::Init_device()
memset(usb_buf, 0x00, sizeof(usb_buf));
usb_buf[0] = JGINYUE_V2_HID_GENERAL_COMMAND_HEADER;
usb_buf[1] = 0x0F;
hid_write(jy_hid_interface, usb_buf, 64);
std::this_thread::sleep_for(20ms);
hid_read(jy_hid_interface, usb_buf, 64);
if(usb_buf[1] != 0x0F)
int write_result = hid_write(jy_hid_interface, usb_buf, 64);
if(write_result < 0)
{
LOG_ERROR("[JGINYUEInternalUSBV2Controller] Failed to write to JGINYUE device during initialization");
ZoneCount = 0x00;
memset(device_config, 0x00, sizeof(device_config));
memset (&device_config_Global, 0x00, sizeof(device_config_Global));
memset(&device_config_Global, 0x00, sizeof(device_config_Global));
return;
}
std::this_thread::sleep_for(20ms);
int bytes_read = hid_read_timeout(jy_hid_interface, usb_buf, 64, 1000);
if(bytes_read <= 0 || usb_buf[1] != 0x0F)
{
LOG_ERROR("[JGINYUEInternalUSBV2Controller] JGINYUE device did not respond or invalid response (bytes read: %d)", bytes_read);
ZoneCount = 0x00;
memset(device_config, 0x00, sizeof(device_config));
memset(&device_config_Global, 0x00, sizeof(device_config_Global));
return;
}
unsigned char Zone_Info = usb_buf[4];
@@ -135,13 +149,25 @@ void JGINYUEInternalUSBV2Controller::Init_Zone(int zone)
usb_buf[1] = JGINYUE_V2_HID_REQUEST_ARGB_SETTING;
usb_buf[2] = Area_ID;
hid_write(jy_hid_interface, usb_buf, 64);
int write_result = hid_write(jy_hid_interface, usb_buf, 64);
if(write_result < 0)
{
LOG_ERROR("[JGINYUEInternalUSBV2Controller] Failed to write to JGINYUE device for zone %d", zone);
return;
}
std::this_thread::sleep_for(20ms);
hid_read(jy_hid_interface, usb_buf, 64);
if((usb_buf[1] != JGINYUE_V2_HID_REQUEST_ARGB_SETTING)|(usb_buf[2] != Area_ID))
int bytes_read = hid_read_timeout(jy_hid_interface, usb_buf, 64, 1000);
if(bytes_read <= 0)
{
LOG_ERROR("[JGINYUEInternalUSBV2Controller] Failed to read zone %d config from JGINYUE device (bytes read: %d)", zone, bytes_read);
return;
}
if((usb_buf[1] != JGINYUE_V2_HID_REQUEST_ARGB_SETTING) || (usb_buf[2] != Area_ID))
{
LOG_ERROR("[JGINYUEInternalUSBV2Controller] Invalid response for zone %d from JGINYUE device", zone);
return;
}
@@ -200,6 +226,16 @@ void JGINYUEInternalUSBV2Controller::DirectLEDControl
unsigned char Area
)
{
/*-----------------------------------------------------*\
| Direct mode requires CDC interface |
| If CDC is not available, log error and return |
\*-----------------------------------------------------*/
if(jy_cdc_interface == nullptr)
{
LOG_WARNING("[JGINYUEInternalUSBV2Controller] Direct mode requires serial port (CDC) which is not available. Use other modes instead.");
return;
}
unsigned char cdc_buf[512];
memset(cdc_buf, 0x00, sizeof(cdc_buf));
cdc_buf[0] = JGINYUE_V2_CDC_COMMAND_HEADER;
@@ -46,30 +46,49 @@ void DetectJGINYUEInternalUSBV2Controller(hid_device_info* info,const std::strin
std::transform(manufacturer.begin(), manufacturer.end(), manufacturer.begin(), ::toupper);
if(manufacturer.find("JGINYUE") == std::string::npos)
{
LOG_INFO("JGINYUE Internal USB ControllerV2 not found,error manufacturer name:%s",manufacturer.c_str());
LOG_INFO("[JGINYUEInternalUSBV2ControllerDetect] JGINYUE Internal USB ControllerV2 not found,error manufacturer name:%s",manufacturer.c_str());
hid_close(hid_dev);
return;
}
LOG_INFO("Pass manufacture name check.Start to init HID and CDC interface");
LOG_INFO("[JGINYUEInternalUSBV2ControllerDetect] Pass manufacture name check.Start to init HID and CDC interface");
if(hid_dev != nullptr )
{
serial_port *port = nullptr;
std::vector<std::string*> serial_ports = find_usb_serial_port(JGINYUE_VID_V2, JGINYUE_MOTHERBOARD_PID_V2);
if(serial_ports.size() ==1)
if(serial_ports.size() == 0)
{
serial_port *port = new serial_port();
LOG_WARNING("[JGINYUEInternalUSBV2ControllerDetect] JGINYUE device found but no serial port detected - Direct mode will be unavailable");
}
else if(serial_ports.size() > 1)
{
LOG_WARNING("[JGINYUEInternalUSBV2ControllerDetect] Multiple serial ports found for JGINYUE device, using first one");
}
if(serial_ports.size() >= 1)
{
port = new serial_port();
if(!port->serial_open(serial_ports[0]->c_str(), 115200))
{
LOG_ERROR("Failed to open serial port %s", serial_ports[0]->c_str());
LOG_WARNING("[JGINYUEInternalUSBV2ControllerDetect] Failed to open serial port %s - Direct mode will be unavailable. HID modes will still work.", serial_ports[0]->c_str());
delete port;
hid_close(hid_dev);
return;
port = nullptr;
}
JGINYUEInternalUSBV2Controller *controller = new JGINYUEInternalUSBV2Controller(hid_dev, info->path,port);
RGBController_JGINYUEInternalUSBV2 *rgb_controller = new RGBController_JGINYUEInternalUSBV2(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
LOG_INFO("JGINYUE Internal USB ControllerV2 found");
}
/*-----------------------------------------------------*\
| Clean up serial port string vector |
\*-----------------------------------------------------*/
for(std::string* str_ptr : serial_ports)
{
delete str_ptr;
}
JGINYUEInternalUSBV2Controller *controller = new JGINYUEInternalUSBV2Controller(hid_dev, info->path, port);
RGBController_JGINYUEInternalUSBV2 *rgb_controller = new RGBController_JGINYUEInternalUSBV2(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
}
}
@@ -318,7 +318,7 @@ void RGBController_LenovoK510::ReadAndUpdateCurrentDeviceState()
current_active_mode.direction = current_active_mode.direction ? MODE_DIRECTION_UP : MODE_DIRECTION_DOWN;
}
active_mode = i;
active_mode = (int)i;
break;
}
}
@@ -286,15 +286,15 @@ LenovoRGBController_Gen7_8::LenovoRGBController_Gen7_8(LenovoGen7And8USBControll
SetupZones();
/*-----------------*\
| Initiliaze Static |
\*-----------------*/
/*-----------------------------------------------------*\
| Initiliaze Static |
\*-----------------------------------------------------*/
active_mode = 0;
for(size_t i = 0; i < modes.size(); i++)
{
if(modes[i].value == LENOVO_LEGION_GEN7_8_MODE_STATIC)
{
active_mode = i;
active_mode = (int)i;
break;
}
}
@@ -307,7 +307,6 @@ LenovoRGBController_Gen7_8::~LenovoRGBController_Gen7_8()
delete controller;
}
void LenovoRGBController_Gen7_8::SetupZones()
{
vector<lenovo_zone> lenovo_zones;
@@ -363,9 +362,9 @@ void LenovoRGBController_Gen7_8::SetupZones()
new_led.value = lenovo_zones[i].id << 8 | lenovo_zones[i].leds[led_idx].led_num ;
leds.push_back(new_led);
/*---------------------------------------------------------*\
| create led id to index map for fast look up |
\*---------------------------------------------------------*/
/*---------------------------------------------*\
| create led id to index map for fast look up |
\*---------------------------------------------*/
led_id_to_index[new_led.value]=leds.size() - 1;
}
}
@@ -449,9 +448,10 @@ void LenovoRGBController_Gen7_8::DeviceUpdateLEDs()
{
if(controller->getPid() == LEGION_7GEN10)
{
/*---------------------------------------------------------*\
| Gen10 may ignore A1 updates unless D0 is reasserted. |
\*---------------------------------------------------------*/
/*---------------------------------------------*\
| Gen10 may ignore A1 updates unless D0 is |
| reasserted. |
\*---------------------------------------------*/
controller->setLedsDirectOn(profile_id);
direct_enabled = true;
}
@@ -585,9 +585,9 @@ std::vector<led_group> LenovoRGBController_Gen7_8::GetLedGroups()
size_t start = 0;
size_t end = leds.size();
/*---------------------------------------------------------*\
| Riplle and Type only apply to keyboard |
\*---------------------------------------------------------*/
/*-------------------------------------------------*\
| Riplle and Type only apply to keyboard |
\*-------------------------------------------------*/
if(modes[active_mode].value == LENOVO_LEGION_GEN7_8_MODE_RIPPLE ||
modes[active_mode].value == LENOVO_LEGION_GEN7_8_MODE_TYPE)
{
@@ -291,7 +291,7 @@ void LianLiUniHubSLController::SendActivate(size_t channel, unsigned char num_fa
buf[0x00] = UNIHUB_SL_REPORT_ID;
buf[0x01] = 0x10;
buf[0x02] = 0x32;
buf[0x03] = 0x10 * channel + num_fans;
buf[0x03] = 0x10 * (unsigned char)channel + num_fans;
this->LogBuffer("SendActivate", buf, sizeof(buf));
@@ -329,10 +329,10 @@ void LianLiUniHubSLController::SendMerge()
void LianLiUniHubSLController::SendColor(size_t channel, const unsigned char *colors, size_t num_colors)
{
unsigned char* buf = new unsigned char[2 + num_colors];
memset(buf, 0x00, sizeof(buf));
memset(buf, 0x00, (2 + num_colors));
buf[0x00] = UNIHUB_SL_REPORT_ID;
buf[0x01] = 0x30 + channel; // Channel 1: 0x30, Channel 2: 0x31, etc.
buf[0x01] = 0x30 + (unsigned char)channel; // Channel 1: 0x30, Channel 2: 0x31, etc.
memcpy(&buf[0x02], colors, num_colors);
@@ -350,7 +350,7 @@ void LianLiUniHubSLController::SendMode(size_t channel, const mode &active)
memset(buf, 0x00, sizeof(buf));
buf[0x00] = UNIHUB_SL_REPORT_ID;
buf[0x01] = 0x10 + channel; // Channel 1: 0x10, Channel 2: 0x11, etc.
buf[0x01] = 0x10 + (unsigned char)channel; // Channel 1: 0x10, Channel 2: 0x11, etc.
buf[0x02] = active.value;
buf[0x03] = this->ConvertSpeed(active.speed);
buf[0x04] = this->ConvertDirection(active.direction);
@@ -321,7 +321,7 @@ void RGBController_LianLiUniHubSL::SetupZones()
new_led.name = zones[zone_idx].name;
new_led.name.append(", Fan ");
new_led.name.append(std::to_string(led_idx + 1));
new_led.value = zone_idx;
new_led.value = (unsigned int)zone_idx;
leds.push_back(new_led);
}
@@ -66,7 +66,7 @@ std::string LianLiUniversalScreenController::GetVersion()
void LianLiUniversalScreenController::SetLedColors(RGBColor* colors, size_t count)
{
unsigned char leds_in_packet = 20;
std::size_t leds_in_packet = 20;
unsigned char offset = 0;
unsigned char usb_buf[64];
@@ -91,7 +91,7 @@ void LianLiUniversalScreenController::SetLedColors(RGBColor* colors, size_t coun
usb_buf[6 + (led_idx * 3)] = RGBGetBValue(colors[offset + led_idx]);
}
offset += leds_in_packet;
offset += (unsigned char)leds_in_packet;
int actual_length = sizeof(usb_buf);
libusb_bulk_transfer(dev, 1, usb_buf, sizeof(usb_buf), &actual_length, 25);
@@ -38,6 +38,7 @@ void DetectMSIGPUv2Controllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const
} /* DetectMSIGPUv2Controllers() */
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4060 Gaming X", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4060_DEV, MSI_SUB_VEN, MSI_RTX4060_GAMING_X_8G_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4060 Gaming X NV Edition", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4060_DEV, MSI_SUB_VEN, MSI_RTX4060_GAMING_X_NV_EDITION_8G_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4060 Ti Gaming X", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4060TI_DEV, MSI_SUB_VEN, MSI_RTX4060TI_GAMING_X_8G_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4060 Ti 16GB Gaming X", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4060TI_16G_DEV, MSI_SUB_VEN, MSI_RTX4060TI_GAMING_X_16G_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4060 Ti 16GB Gaming X Slim White", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4060TI_16G_DEV, MSI_SUB_VEN, MSI_RTX4060TI_GAMING_X_16G_SLIM_WHITE_SUB_DEV, 0x68);
@@ -67,6 +68,7 @@ REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4090 Gaming X Slim",
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4090 Suprim Liquid X", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4090_DEV, MSI_SUB_VEN, MSI_RTX4090_SUPRIM_LIQUID_X_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 4090 Suprim X", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX4090_DEV, MSI_SUB_VEN, MSI_RTX4090_SUPRIM_X_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 5070 Ti Gaming Trio OC Plus", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, MSI_SUB_VEN, MSI_RTX5070TI_GAMING_TRIO_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 5070 Ti VANGUARD SOC", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, MSI_SUB_VEN, MSI_RTX5070TI_VANGUARD_SOC_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 5080 Gaming Trio OC", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, MSI_SUB_VEN, MSI_RTX5080_GAMING_TRIO_OC_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 5080 VANGUARD OC SOC", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, MSI_SUB_VEN, MSI_RTX5080_VANGUARD_SOC_SUB_DEV, 0x68);
REGISTER_I2C_PCI_DETECTOR("MSI GeForce RTX 5080 SUPRIM SOC", DetectMSIGPUv2Controllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, MSI_SUB_VEN, MSI_RTX5080_SUPRIM_SOC_SUB_DEV, 0x68);
@@ -227,6 +227,11 @@ const std::vector<MSI_ZONE> zones_set19 =
MSI_ZONE_J_RAINBOW_3
};
const std::vector<MSI_ZONE> zones_set20 =
{
MSI_ZONE_J_RGB_1,
};
/*---------------------------------------------------------------------------------------------------------------------------------*\
| Definition of the board sepcific configurations (number of onboard LEDs and supported zones). |
@@ -312,6 +317,7 @@ static const mystic_light_185_config board_configs[] =
{ 0x7D77, 0, 0, 0, 2, &zones_set13, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // PRO B650M-A WIFI
{ 0x7D78, 0, 0, 0, 2, &zones_set13, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // PRO B650-P WIFI
{ 0x7D86, 0, 18, 4, 1, &zones_set16, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // MEG Z790 ACE
{ 0x7D88, 0, 0, 0, 1, &zones_set20, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // MPG Z790-S WIFI
{ 0x7D89, 0, 6, 0, 1, &zones_set18, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // MPG Z790 CARBON WIFI
{ 0x7D90, 0, 0, 0, 1, &zones_set11, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // B760M BOMBER DDR4
{ 0x7D91, 1, 0, 0, 1, &zones_set10, MSIMysticLight185Controller::DIRECT_MODE_PER_LED }, // MAG Z790 TOMAHAWK WIFI
@@ -62,6 +62,10 @@ static const std::string board_names[] =
"MSI PRO X870E-P WIFI (MS-7E70)",
"MSI MPG X870I EDGE TI EVO WIFI (MS-7E50)",
"MSI B850 GAMING PLUS WIFI (MS-7E56)",
"MSI PRO X870-P WIFI (MS-7E47)",
"MSI MPG X870E EDGE TI WIFI (MS-7E59)",
"MSI MAG B850 TOMAHAWK MAX WIFI (MS-7E62)",
"MSI PRO B850M-P WIFI (MS-7E71)"
};
static const mystic_light_761_config board_configs[] =
@@ -81,6 +85,10 @@ static const mystic_light_761_config board_configs[] =
{ &(board_names[12]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI PRO X870E-P WIFI
{ &(board_names[13]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI MPG X870I EDGE TI EVO WIFI (MS-7E50)
{ &(board_names[14]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI B850 GAMING PLUS WIFI (MS-7E56)
{ &(board_names[15]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI PRO X870-P WIFI
{ &(board_names[16]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI MPG X870E EDGE TI WIFI
{ &(board_names[17]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI MAG B850 TOMAHAWK MAX WIFI
{ &(board_names[18]), 0, 0, 0, 1, &zone_set1, MSIMysticLight761Controller::DIRECT_MODE_ZONE_BASED }, // MSI PRO B850M-P WIFI (MS-7E71)
};
enum MSI_ZONE setup_map [] =
@@ -231,6 +231,7 @@ REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D76", DetectMSIMysticLightCont
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D77", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D77, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D78", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D78, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D86", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D86, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D88", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D88, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D89", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D89, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D90", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D90, 0x0001, 0x00);
REGISTER_HID_DETECTOR_PU("MSI Mystic Light MS_7D91", DetectMSIMysticLightControllers, MSI_USB_VID, 0x7D91, 0x0001, 0x00);
@@ -22,6 +22,19 @@ Mountain60KeyboardController::Mountain60KeyboardController(hid_device* dev_handl
dev = dev_handle;
location = path;
name = dev_name;
unsigned char usb_buf[MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE];
unsigned char read[MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE];
memset(usb_buf, 0x00, MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE);
usb_buf[0x01] = MOUNTAIN60_KEYBOARD_RESET_CMD;
usb_buf[0x02] = 0x46; //constant data
usb_buf[0x03] = 0x23; //constant data
usb_buf[0x04] = 0xEA; //constant data
hid_send_feature_report(dev, usb_buf, MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE);
memset(read, 0x00, MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE);
hid_get_feature_report(dev, read, MOUNTAIN60_KEYBOARD_USB_BUFFER_SIZE);
}
Mountain60KeyboardController::~Mountain60KeyboardController()
@@ -26,6 +26,7 @@
enum
{
MOUNTAIN60_KEYBOARD_RESET_CMD = 0x03,
MOUNTAIN60_KEYBOARD_CHECK_NUMPAD = 0x08,
MOUNTAIN60_KEYBOARD_SELECT_MODE_CMD = 0x16,
MOUNTAIN60_KEYBOARD_SEND_CMD = 0x17,
@@ -15,9 +15,9 @@
using namespace std::chrono_literals;
/*-------------------------------*\
| TODO: Detect detached keypad |
\*-------------------------------*/
/*---------------------------------------------------------*\
| TODO: Detect detached keypad |
\*---------------------------------------------------------*/
std::vector<unsigned int> mountain60_keyboard_key_id_values =
{
@@ -37,9 +37,9 @@ layout_values mountain60_layout =
{
mountain60_keyboard_key_id_values,
{
/*------------------------------------------*\
| No regional layout fix for the moment |
\*------------------------------------------*/
/*---------------------------------------------*\
| No regional layout fix for the moment |
\*---------------------------------------------*/
},
};
@@ -348,9 +348,9 @@ RGBController_Mountain60Keyboard::~RGBController_Mountain60Keyboard()
mountain_thread->join();
delete mountain_thread;
/*---------------------------------------------------------*\
| Delete the matrix map |
\*---------------------------------------------------------*/
/*-----------------------------------------------------*\
| Delete the matrix map |
\*-----------------------------------------------------*/
for(unsigned int zone_index = 0; zone_index < zones.size(); zone_index++)
{
if(zones[zone_index].type == ZONE_TYPE_MATRIX)
@@ -406,10 +406,10 @@ void RGBController_Mountain60Keyboard::DeviceUpdateLEDs()
{
unsigned char* color_data = new unsigned char[(leds.size()*4)];
/*---------------------------------------------------------*\
| Filling the color_data vector with progressive index |
| leaving space for RGB data |
\*---------------------------------------------------------*/
/*-----------------------------------------------------*\
| Filling the color_data vector with progressive index |
| leaving space for RGB data |
\*-----------------------------------------------------*/
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
{
const unsigned int idx = led_idx * 4;
@@ -419,7 +419,7 @@ void RGBController_Mountain60Keyboard::DeviceUpdateLEDs()
color_data[idx + 3] = RGBGetBValue(colors[led_idx]);
}
controller->SendDirect(modes[active_mode].brightness, color_data, (leds.size()*4));
controller->SendDirect(modes[active_mode].brightness, color_data, ((unsigned int)leds.size() * 4));
delete[] color_data;
}
@@ -12,11 +12,12 @@
#include "PNYARGBEpicXGPUController.h"
PNYARGBEpicXGPUController::PNYARGBEpicXGPUController(i2c_smbus_interface* bus, unsigned char init_i2c_addr, std::string name)
PNYARGBEpicXGPUController::PNYARGBEpicXGPUController(i2c_smbus_interface* bus, unsigned char init_i2c_addr, std::string name, bool large_variant)
{
this->bus = bus;
this->i2c_addr = init_i2c_addr;
this->name = name;
this->bus = bus;
this->i2c_addr = init_i2c_addr;
this->name = name;
this->large_variant = large_variant;
}
PNYARGBEpicXGPUController::~PNYARGBEpicXGPUController()
@@ -39,9 +40,14 @@ std::string PNYARGBEpicXGPUController::GetDeviceName()
return(name);
}
bool PNYARGBEpicXGPUController::IsLargeVariant()
{
return(large_variant);
}
void PNYARGBEpicXGPUController::SetZoneMode(unsigned char zone, unsigned char mode, unsigned char speed, unsigned char brightness, unsigned char subcmd, RGBColor color)
{
unsigned char data[7] =
unsigned char data[7] =
{
mode,
brightness,
@@ -69,4 +75,4 @@ void PNYARGBEpicXGPUController::SetLEDDirect(unsigned char zone, unsigned char l
};
bus->i2c_smbus_write_i2c_block_data(i2c_addr, zone, sizeof(data), data);
}
}
@@ -45,12 +45,14 @@ enum
class PNYARGBEpicXGPUController
{
public:
PNYARGBEpicXGPUController(i2c_smbus_interface* bus, unsigned char init_i2c_addr, std::string name);
PNYARGBEpicXGPUController(i2c_smbus_interface* bus, unsigned char init_i2c_addr, std::string name, bool large_variant);
~PNYARGBEpicXGPUController();
std::string GetDeviceLocation();
std::string GetDeviceName();
bool IsLargeVariant();
void SetZoneMode(unsigned char zone, unsigned char mode, unsigned char speed, unsigned char brightness, unsigned char subcmd, RGBColor color);
void SetLEDDirect(unsigned char zone, unsigned char led, unsigned char mode, RGBColor color);
@@ -58,4 +60,5 @@ private:
i2c_smbus_interface* bus;
unsigned char i2c_addr;
std::string name;
bool large_variant;
};
@@ -11,29 +11,35 @@
\*---------------------------------------------------------*/
#include "Detector.h"
#include "i2c_smbus.h"
#include "LogManager.h"
#include "pci_ids.h"
#include "PNYARGBEpicXGPUController.h"
#include "RGBController_PNYARGBEpicXGPU.h"
#include "i2c_smbus.h"
#include "pci_ids.h"
/*-----------------------------------------------------------------------------------------*\
| DetectPNYARGBEpicXGPUControllers |
| |
| Detect PNY ARGB Epic X GPU controllers on the enumerated I2C busses at address 0x60. |
| |
| bus - pointer to i2c_smbus_interface where PNY GPU device is connected |
| dev - I2C address of PNY GPU device |
\*-----------------------------------------------------------------------------------------*/
void DetectPNYARGBEpicXGPUControllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
void DetectPNYARGBEpicXGPUSmallControllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
{
PNYARGBEpicXGPUController* controller = new PNYARGBEpicXGPUController(bus, i2c_addr, name);
RGBController_PNYARGBEpicXGPU* rgb_controller = new RGBController_PNYARGBEpicXGPU(controller);
if(bus->port_id == 1)
{
PNYARGBEpicXGPUController* controller = new PNYARGBEpicXGPUController(bus, i2c_addr, name, false);
RGBController_PNYARGBEpicXGPU* rgb_controller = new RGBController_PNYARGBEpicXGPU(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
} /* DetectPNYARGBEpicXGPUControllers() */
ResourceManager::get()->RegisterRGBController(rgb_controller);
}
}
REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5070Ti ARGB Epic-X OC", DetectPNYARGBEpicXGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, PNY_SUB_VEN, PNY_RTX_5070TI_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
//REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5080 ARGB Epic-X OC", DetectPNYARGBEpicXGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, PNY_SUB_VEN, PNY_RTX_5080_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
//REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5090 ARGB Epic-X OC", DetectPNYARGBEpicXGPUControllers, NVIDIA_VEN, NVIDIA_RTX5090_DEV, PNY_SUB_VEN, PNY_RTX_5090_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
void DetectPNYARGBEpicXGPULargeControllers(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
{
if(bus->port_id == 1)
{
PNYARGBEpicXGPUController* controller = new PNYARGBEpicXGPUController(bus, i2c_addr, name, true);
RGBController_PNYARGBEpicXGPU* rgb_controller = new RGBController_PNYARGBEpicXGPU(controller);
ResourceManager::get()->RegisterRGBController(rgb_controller);
}
}
REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5070 ARGB Epic-X OC", DetectPNYARGBEpicXGPUSmallControllers, NVIDIA_VEN, NVIDIA_RTX5070_DEV, PNY_SUB_VEN, PNY_RTX_5070_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5070Ti ARGB Epic-X OC", DetectPNYARGBEpicXGPUSmallControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, PNY_SUB_VEN, PNY_RTX_5070TI_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5080 ARGB Epic-X OC", DetectPNYARGBEpicXGPULargeControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, PNY_SUB_VEN, PNY_RTX_5080_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
REGISTER_I2C_PCI_DETECTOR("PNY GeForce RTX 5090 ARGB Epic-X OC", DetectPNYARGBEpicXGPULargeControllers, NVIDIA_VEN, NVIDIA_RTX5090_DEV, PNY_SUB_VEN, PNY_RTX_5090_ARGB_EPIC_X_OC_SUB_DEV, 0x60);
@@ -28,24 +28,115 @@
RGBController_PNYARGBEpicXGPU::RGBController_PNYARGBEpicXGPU(PNYARGBEpicXGPUController* controller_ptr)
{
controller = controller_ptr;
controller = controller_ptr;
name = controller->GetDeviceName();
vendor = "PNY";
description = "PNY ARGB Epic-X GPU Device";
location = controller->GetDeviceLocation();
type = DEVICE_TYPE_GPU;
name = controller->GetDeviceName();
vendor = "PNY";
description = "PNY ARGB Epic-X GPU Device";
location = controller->GetDeviceLocation();
type = DEVICE_TYPE_GPU;
mode Direct;
Direct.name = "Direct";
Direct.value = PNY_GPU_MODE_ARGB_DIRECT;
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
Direct.color_mode = MODE_COLORS_PER_LED;
Direct.brightness = 0xFF;
Direct.brightness_min = 0;
Direct.brightness_max = 0xFF;
Direct.name = "Direct";
Direct.value = PNY_GPU_MODE_ARGB_DIRECT;
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
Direct.color_mode = MODE_COLORS_PER_LED;
modes.push_back(Direct);
mode Off;
Off.name = "Off";
Off.value = PNY_GPU_MODE_ARGB_OFF;
Off.color_mode = MODE_COLORS_NONE;
modes.push_back(Off);
mode Cycle;
Cycle.name = "Spectrum Cycle";
Cycle.value = PNY_GPU_MODE_ARGB_CYCLE;
Cycle.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Cycle.color_mode = MODE_COLORS_RANDOM;
Cycle.speed = 0x09;
Cycle.speed_min = 0x0F;
Cycle.speed_max = 0x00;
Cycle.brightness = 0xFF;
Cycle.brightness_min = 0;
Cycle.brightness_max = 0xFF;
modes.push_back(Cycle);
mode Neon;
Neon.name = "Neon";
Neon.value = PNY_GPU_MODE_ARGB_NEON;
Neon.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Neon.color_mode = MODE_COLORS_RANDOM;
Neon.speed = 0x09;
Neon.speed_min = 0x5F;
Neon.speed_max = 0x00;
Neon.brightness = 0xFF;
Neon.brightness_min = 0;
Neon.brightness_max = 0xFF;
modes.push_back(Neon);
// mode Explosion;
// Explosion.name = "Explosion";
// Explosion.value = PNY_GPU_MODE_ARGB_EXPLOSION;
// Explosion.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
// Explosion.color_mode = MODE_COLORS_MODE_SPECIFIC;
// Explosion.brightness = 0xFF;
// Explosion.brightness_min = 0;
// Explosion.brightness_max = 0xFF;
// Explosion.colors_min = 1;
// Explosion.colors_max = 1;
// Explosion.colors.resize(1);
// modes.push_back(Explosion);
// mode Supernova;
// Supernova.name = "Supernova";
// Supernova.value = PNY_GPU_MODE_ARGB_SUPERNOVA;
// Supernova.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
// Supernova.color_mode = MODE_COLORS_RANDOM;
// Supernova.brightness = 0xFF;
// Supernova.brightness_min = 0;
// Supernova.brightness_max = 0xFF;
// modes.push_back(Supernova);
mode Infinity;
Infinity.name = "Infinity";
Infinity.value = PNY_GPU_MODE_ARGB_INFINITY;
Infinity.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Infinity.color_mode = MODE_COLORS_RANDOM;
Infinity.speed = 0x09;
Infinity.speed_min = 0x5F;
Infinity.speed_max = 0x00;
Infinity.brightness = 0xFF;
Infinity.brightness_min = 0;
Infinity.brightness_max = 0xFF;
modes.push_back(Infinity);
mode Streamer;
Streamer.name = "Streamer";
Streamer.value = PNY_GPU_MODE_ARGB_STREAMER;
Streamer.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Streamer.color_mode = MODE_COLORS_RANDOM;
Streamer.speed = 0x09;
Streamer.speed_min = 0x5F;
Streamer.speed_max = 0x00;
Streamer.brightness = 0xFF;
Streamer.brightness_min = 0;
Streamer.brightness_max = 0xFF;
modes.push_back(Streamer);
mode Wave;
Wave.name = "Rainbow Wave";
Wave.value = PNY_GPU_MODE_ARGB_WAVE;
Wave.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
Wave.color_mode = MODE_COLORS_RANDOM;
Wave.speed = 0x09;
Wave.speed_min = 0x5F;
Wave.speed_max = 0x00;
Wave.brightness = 0xFF;
Wave.brightness_min = 0;
Wave.brightness_max = 0xFF;
modes.push_back(Wave);
SetupZones();
active_mode = 0;
@@ -59,26 +150,39 @@ RGBController_PNYARGBEpicXGPU::~RGBController_PNYARGBEpicXGPU()
void RGBController_PNYARGBEpicXGPU::SetupZones()
{
/*-----------------------------------------------------*\
| The logo zone has 4 LEDs, but they are part of the |
| FRONT register zone |
| The side logo zone has 4 LEDs, but they are part of |
| the FRONT register zone |
| |
| This card has two variants, large and small. Large |
| is used on the 5080 and 5090 and has an extra logo |
| zone on the rear of the card as well as additional |
| LEDs in the arrow zone. The small variant is used on |
| the 5070 Ti and lower cards. |
\*-----------------------------------------------------*/
zone logo;
logo.name = "Logo";
logo.type = ZONE_TYPE_LINEAR;
logo.leds_min = 4;
logo.leds_max = 4;
logo.leds_count = 4;
logo.matrix_map = NULL;
zones.push_back(logo);
zone side_logo;
for(std::size_t led_idx = 0; led_idx < logo.leds_count; led_idx++)
if(controller->IsLargeVariant())
{
led logo_led;
side_logo.name = "Side Logo";
}
else
{
side_logo.name = "Logo";
}
logo_led.name = "Logo LED " + std::to_string(led_idx);
logo_led.value = PNY_GPU_REG_ZONE_FRONT;
side_logo.type = ZONE_TYPE_LINEAR;
side_logo.leds_min = 4;
side_logo.leds_max = 4;
side_logo.leds_count = 4;
side_logo.matrix_map = NULL;
zones.push_back(side_logo);
leds.push_back(logo_led);
for(std::size_t led_idx = 0; led_idx < side_logo.leds_count; led_idx++)
{
led side_logo_led;
side_logo_led.name = side_logo.name + " LED " + std::to_string(led_idx);
side_logo_led.value = PNY_GPU_REG_ZONE_FRONT;
leds.push_back(side_logo_led);
zone_led_idx.push_back((unsigned char)(led_idx + 20));
}
@@ -98,37 +202,67 @@ void RGBController_PNYARGBEpicXGPU::SetupZones()
for(std::size_t led_idx = 0; led_idx < front.leds_count; led_idx++)
{
led front_led;
front_led.name = "Front LED " + std::to_string(led_idx);
front_led.value = PNY_GPU_REG_ZONE_FRONT;
leds.push_back(front_led);
zone_led_idx.push_back((unsigned char)led_idx);
}
/*-----------------------------------------------------*\
| The arrow zone has 17 LEDs |
| The arrow zone has 17 LEDs on the small variant, 19 |
| LEDs on the large variant |
\*-----------------------------------------------------*/
unsigned int arrow_led_count;
if(controller->IsLargeVariant())
{
arrow_led_count = 19;
}
else
{
arrow_led_count = 17;
}
zone arrow;
arrow.name = "Arrow";
arrow.type = ZONE_TYPE_LINEAR;
arrow.leds_min = 17;
arrow.leds_max = 17;
arrow.leds_count = 17;
arrow.leds_min = arrow_led_count;
arrow.leds_max = arrow_led_count;
arrow.leds_count = arrow_led_count;
arrow.matrix_map = NULL;
zones.push_back(arrow);
for(std::size_t led_idx = 0; led_idx < arrow.leds_count; led_idx++)
{
led arrow_led;
arrow_led.name = "Arrow LED " + std::to_string(led_idx);
arrow_led.value = PNY_GPU_REG_ZONE_ARROW;
leds.push_back(arrow_led);
zone_led_idx.push_back((unsigned char)led_idx);
}
/*-----------------------------------------------------*\
| The rear logo zone is only present on the large |
| variant |
\*-----------------------------------------------------*/
if(controller->IsLargeVariant())
{
zone rear_logo;
rear_logo.name = "Rear Logo";
rear_logo.type = ZONE_TYPE_SINGLE;
rear_logo.leds_min = 1;
rear_logo.leds_max = 1;
rear_logo.leds_count = 1;
rear_logo.matrix_map = NULL;
zones.push_back(rear_logo);
led rear_logo_led;
rear_logo_led.name = "Rear Logo LED";
rear_logo_led.value = PNY_GPU_REG_ZONE_LOGO;
leds.push_back(rear_logo_led);
zone_led_idx.push_back(0);
}
SetupColors();
}
@@ -162,15 +296,36 @@ void RGBController_PNYARGBEpicXGPU::UpdateSingleLED(int led)
void RGBController_PNYARGBEpicXGPU::DeviceUpdateMode()
{
if(modes[active_mode].color_mode == MODE_COLORS_NONE || modes[active_mode].color_mode == MODE_COLORS_RANDOM)
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_FRONT, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, 0);
controller->SetZoneMode(PNY_GPU_REG_ZONE_ARROW, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, 0);
if(controller->IsLargeVariant())
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_LOGO, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, 0);
}
}
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_FRONT, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, modes[active_mode].colors[0]);
controller->SetZoneMode(PNY_GPU_REG_ZONE_ARROW, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, modes[active_mode].colors[0]);
if(controller->IsLargeVariant())
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_LOGO, modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, 0, modes[active_mode].colors[0]);
}
}
else if(modes[active_mode].color_mode == MODE_COLORS_PER_LED)
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_FRONT, modes[active_mode].value, 0, 0xFF, 0, 0);
controller->SetZoneMode(PNY_GPU_REG_ZONE_ARROW, modes[active_mode].value, 0, 0xFF, 0, 0);
if(controller->IsLargeVariant())
{
controller->SetZoneMode(PNY_GPU_REG_ZONE_LOGO, modes[active_mode].value, 0, 0xFF, 0, 0);
}
DeviceUpdateLEDs();
}
}
@@ -76,6 +76,7 @@ REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5060 Ti White OC 16GB", DetectPN
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5070 GamingPro", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070_DEV, PALIT_SUB_VEN, PALIT_RTX5070_GAMINGPRO_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5070 Ti GameRock", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, PALIT_SUB_VEN, PALIT_RTX5070TI_GAMEROCK_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5070 Ti GamingPro", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, PALIT_SUB_VEN, PALIT_RTX5070TI_GAMINGPRO_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5070 Ti GamingPro-S", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5070TI_DEV, PALIT_SUB_VEN, PALIT_RTX5070TI_GAMINGPRO_S_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5080 GameRock", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, PALIT_SUB_VEN, PALIT_RTX5080_GAMEROCK_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5080 GamingPro", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5080_DEV, PALIT_SUB_VEN, PALIT_RTX5080_GAMINGPRO_SUB_DEV, 0x49);
REGISTER_I2C_PCI_DETECTOR("Palit GeForce RTX 5090 Gamerock", DetectPNYGPUControllers, NVIDIA_VEN, NVIDIA_RTX5090_DEV, PALIT_SUB_VEN, PALIT_RTX5090_GAMEROCK_SUB_DEV, 0x49);
@@ -24,6 +24,7 @@ static const unsigned char magic_v2[3] = {0x01, 0x32, 0x00};
| The controller reports a unique identifier for V1 and V2. |
| Unfortunately they are on different addresses. Read it |
| for good measure anyways. |
| N.B: Some V2 controllers report the V1 magic. |
\*---------------------------------------------------------*/
void DetectPowerColorRedDevilGPUControllersV1(i2c_smbus_interface* bus, uint8_t i2c_addr, const std::string& name)
@@ -54,7 +55,7 @@ void DetectPowerColorRedDevilGPUControllersV2(i2c_smbus_interface* bus, uint8_t
unsigned char data[3];
int ret = bus->i2c_smbus_read_i2c_block_data(i2c_addr, RED_DEVIL_V2_READ_REG_MAGIC, 3, data);
if(ret == 3 && memcmp(data, magic_v2, 3) == 0)
if(ret == 3 && (memcmp(data, magic_v1, 3) == 0 || memcmp(data, magic_v2, 3) == 0))
{
PowerColorRedDevilV2Controller* controller = new PowerColorRedDevilV2Controller(bus, i2c_addr, name);
RGBController_PowerColorRedDevilV2* rgb_controller = new RGBController_PowerColorRedDevilV2(controller);
@@ -136,7 +136,7 @@ RGBController_QMKVialRGB::RGBController_QMKVialRGB(QMKVialRGBController* control
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
{
hsv_t hsv_color;
hsv_color.hue = ((float)cur_hue * (360.0f / 256.0f));
hsv_color.hue = (unsigned int)((float)cur_hue * (360.0f / 256.0f));
hsv_color.saturation = cur_sat;
hsv_color.value = cur_val;
@@ -227,7 +227,7 @@ void RGBController_QMKVialRGB::ResizeZone(int /*zone*/, int /*new_size*/)
void RGBController_QMKVialRGB::DeviceUpdateLEDs()
{
controller->SendLEDs(colors.size(), colors.data());
controller->SendLEDs((unsigned short)colors.size(), colors.data());
}
void RGBController_QMKVialRGB::UpdateZoneLEDs(int /*zone*/)
@@ -239,6 +239,7 @@ REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V3 Mini (Wireless)", Det
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_PID, 0x03, 0x01, 0x00);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4 Pro", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_PRO_PID, 0x03, 0x01, 0x00);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4 Pro 75% (Wired)", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_PRO_75_WIRED_PID, 0x03, 0x0C, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4 Pro 75% (Wireless)", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_PRO_75_WIRELESS_PID, 0x02, 0x01, 0x02);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4 75% (Wired)", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_75_WIRED_PID, 0x03, 0x01, 0x00);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow V4 X", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_V4_X_PID, 0x02, 0x01, 0x02);
REGISTER_HID_DETECTOR_IPU("Razer Blackwidow X Chroma", DetectRazerControllers, RAZER_VID, RAZER_BLACKWIDOW_X_CHROMA_PID, 0x02, 0x01, 0x02);
@@ -392,6 +393,7 @@ REGISTER_HID_DETECTOR_IPU("Razer Kraken Ultimate", Det
REGISTER_HID_DETECTOR_IPU("Razer Kraken V3 HyperSense", DetectRazerKrakenV3Controllers,RAZER_VID, RAZER_KRAKEN_V3_HYPERSENSE_PID, 0x03, 0x0C, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken V3 X", DetectRazerKrakenV3Controllers,RAZER_VID, RAZER_KRAKEN_V3_X_PID, 0x03, 0x0C, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken V3", DetectRazerKrakenV3Controllers,RAZER_VID, RAZER_KRAKEN_V3_PID, 0x03, 0x0C, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken Kitty V2 Pro", DetectRazerKrakenV3Controllers,RAZER_VID, RAZER_KRAKEN_KITTY_V2_PRO_PID, 0x03, 0x0C, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken V4 (Wired)", DetectRazerKrakenV4Controllers,RAZER_VID, RAZER_KRAKEN_V4_WIRED_PID, 0x05, 0xFF14, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken V4 (Wireless)", DetectRazerKrakenV4Controllers,RAZER_VID, RAZER_KRAKEN_V4_WIRELESS_PID, 0x05, 0xFF14, 0x01);
REGISTER_HID_DETECTOR_IPU("Razer Kraken Kitty V3 Pro (Wired)", DetectRazerKrakenV4Controllers,RAZER_VID, RAZER_KRAKEN_KITTY_V3_PRO_WIRED_PID, 0x05, 0xFF14, 0x01);
+124 -14
View File
@@ -345,7 +345,7 @@ keyboard_keymap_overlay_values razer_blackwidow_v4_pro_layout
}
};
keyboard_keymap_overlay_values razer_blackwidow_v4_pro_75_wired_layout
keyboard_keymap_overlay_values razer_blackwidow_v4_pro_75_layout
{
KEYBOARD_SIZE::KEYBOARD_SIZE_SEVENTY_FIVE,
{
@@ -361,27 +361,34 @@ keyboard_keymap_overlay_values razer_blackwidow_v4_pro_75_wired_layout
\*-------------------------------------------------------------------------------------------------------------------------------------*/
{ 0, 0, 0, 0, "Left Underglow 0", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 0, 2, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Delete gap between ESC and F1
{ 0, 0, 14, 0, "Left Underglow 1", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 0, 15, 0, "Left Underglow 5", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 0, 16, 0, "Left Underglow 8", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 0, 17, 0, "Right Underglow 0", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 1, 0, 0, "Left Underglow 1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 1, 0, 0, "Left Underglow 2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Add gap between = and Backspace
{ 0, 1, 16, 0, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 1, 17, 0, "Right Underglow 1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 2, 0, 0, "Left Underglow 2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 1, 17, 0, "Right Underglow 2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 2, 0, 0, "Left Underglow 3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 2, 16, 0, KEY_EN_PAGE_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 2, 17, 0, "Right Underglow 2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 3, 0, 0, "Left Underglow 3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 2, 17, 0, "Right Underglow 3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 3, 0, 0, "Left Underglow 4", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 3, 16, 0, KEY_EN_PAGE_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 3, 17, 0, "Right Underglow 3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 0, 0, "Left Underglow 4", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 3, 17, 0, "Right Underglow 4", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 0, 0, "Left Underglow 6", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 15, 0, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 16, 0, KEY_EN_INSERT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 17, 0, "Right Underglow 4", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 0, 0, "Left Underglow 5", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 4, 17, 0, "Right Underglow 6", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 0, 0, "Left Underglow 7", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 5, 0, "Right Underglow 1", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 5, 6, 0, "Right Underglow 5", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 5, 8, 0, "Right Underglow 8", KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY },
{ 0, 5, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Menu key between Fn and RCtrl
{ 0, 5, 14, 0, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 15, 0, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 16, 0, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 17, 0, "Right Underglow 5", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
{ 0, 5, 17, 0, "Right Underglow 7", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
}
};
@@ -1817,7 +1824,7 @@ static const razer_device blackwidow_v4_pro_device =
};
/*-------------------------------------------------------------*\
| Razer Blackwidow V4 Pro 75% 1532:02B3 |
| Razer Blackwidow V4 Pro 75% (Wired) 1532:02B3 |
| |
| Zone "Keyboard" |
| Matrix |
@@ -1848,7 +1855,42 @@ static const razer_device blackwidow_v4_pro_75_wired_device =
NULL,
NULL
},
&razer_blackwidow_v4_pro_75_wired_layout
&razer_blackwidow_v4_pro_75_layout
};
/*-------------------------------------------------------------*\
| Razer Blackwidow V4 Pro 75% (Wireless) 1532:02B4 |
| |
| Zone "Keyboard" |
| Matrix |
| 6 Rows, 18 Columns |
\*-------------------------------------------------------------*/
static const razer_zone blackwidow_v4_pro_75_wireless_zone =
{
ZONE_EN_KEYBOARD,
ZONE_TYPE_MATRIX,
6,
18
};
static const razer_device blackwidow_v4_pro_75_wireless_device =
{
"Razer Blackwidow V4 Pro 75% (Wireless)",
RAZER_BLACKWIDOW_V4_PRO_75_WIRELESS_PID,
DEVICE_TYPE_KEYBOARD,
RAZER_MATRIX_TYPE_EXTENDED,
0x1F,
6,
18,
{
&blackwidow_v4_pro_75_wireless_zone,
NULL,
NULL,
NULL,
NULL,
NULL
},
&razer_blackwidow_v4_pro_75_layout
};
/*-------------------------------------------------------------*\
@@ -1883,7 +1925,7 @@ static const razer_device blackwidow_v4_75_wired_device =
NULL,
NULL
},
&razer_blackwidow_v4_pro_75_wired_layout
&razer_blackwidow_v4_pro_75_layout
};
/*-------------------------------------------------------------*\
@@ -7841,6 +7883,72 @@ static const razer_device kraken_v3_device =
NULL
};
/*-------------------------------------------------------------*\
| Razer Kraken Kitty V2 Pro 1532:0554 |
| |
| Zone "Left Cat Ear" |
| Single |
| 1 LED |
| Zone "Right Cat Ear" |
| Single |
| 1 LED |
| Zone "Left Logo" |
| Single |
| 1 LED |
| Zone "Right Logo" |
| Single |
| 1 LED |
\*-------------------------------------------------------------*/
static const razer_zone kraken_kitty_v2_pro_left_ear_zone =
{
"Left Cat Ear",
ZONE_TYPE_SINGLE,
1,
1
};
static const razer_zone kraken_kitty_v2_pro_right_ear_zone =
{
"Right Cat Ear",
ZONE_TYPE_SINGLE,
1,
1
};
static const razer_zone kraken_kitty_v2_pro_left_logo_zone =
{
"Left Logo",
ZONE_TYPE_SINGLE,
1,
1
};
static const razer_zone kraken_kitty_v2_pro_right_logo_zone =
{
"Right Logo",
ZONE_TYPE_SINGLE,
1,
1
};
static const razer_device kraken_kitty_v2_pro_device =
{
"Razer Kraken Kitty V2 Pro",
RAZER_KRAKEN_KITTY_V2_PRO_PID,
DEVICE_TYPE_HEADSET,
RAZER_MATRIX_TYPE_NONE,
0,
1,
4,
{
&kraken_kitty_v2_pro_left_ear_zone,
&kraken_kitty_v2_pro_right_ear_zone,
&kraken_kitty_v2_pro_left_logo_zone,
&kraken_kitty_v2_pro_right_logo_zone,
NULL,
NULL
},
NULL
};
/*-------------------------------------------------------------*\
| Razer Kraken V4 Wired 1532:056B |
| |
@@ -9027,6 +9135,7 @@ const razer_device* razer_device_list[] =
&blackwidow_v4_device,
&blackwidow_v4_pro_device,
&blackwidow_v4_pro_75_wired_device,
&blackwidow_v4_pro_75_wireless_device,
&blackwidow_v4_75_wired_device,
&blackwidow_v4_x_device,
&blackwidow_x_chroma_device,
@@ -9185,6 +9294,7 @@ const razer_device* razer_device_list[] =
&kraken_v3_hs_device,
&kraken_v3_x_device,
&kraken_v3_device,
&kraken_kitty_v2_pro_device,
&kraken_v4_wired_device,
&kraken_v4_wireless_device,
&kraken_kitty_v3_pro_wired_device,
@@ -54,6 +54,7 @@
#define RAZER_BLACKWIDOW_V4_PRO_PID 0x028D
#define RAZER_BLACKWIDOW_V4_X_PID 0x0293
#define RAZER_BLACKWIDOW_V4_PRO_75_WIRED_PID 0x02B3
#define RAZER_BLACKWIDOW_V4_PRO_75_WIRELESS_PID 0x02B4
#define RAZER_BLACKWIDOW_V4_75_WIRED_PID 0x02A5
#define RAZER_BLACKWIDOW_X_CHROMA_PID 0x0216
#define RAZER_BLACKWIDOW_X_CHROMA_TE_PID 0x021A
@@ -228,6 +229,7 @@
#define RAZER_KRAKEN_V3_HYPERSENSE_PID 0x0533
#define RAZER_KRAKEN_V3_X_PID 0x0537
#define RAZER_KRAKEN_V3_PID 0x0549
#define RAZER_KRAKEN_KITTY_V2_PRO_PID 0x0554
#define RAZER_KRAKEN_V4_WIRED_PID 0x056B
#define RAZER_KRAKEN_V4_WIRELESS_PID 0x056C
#define RAZER_KRAKEN_KITTY_V3_PRO_WIRED_PID 0x0587
@@ -161,7 +161,7 @@ void RazerKrakenV3Controller::SetModeBreathing(std::vector<RGBColor> colors)
{
razer_kraken_v3_request_report report = razer_kraken_create_v3_report();
unsigned char led_count = colors.size();
unsigned char led_count = (unsigned char)colors.size();
// 0 1 2 3 4 5 6 7 8 9 0 1 2
// 400101000101ff000000000000
@@ -35,7 +35,7 @@ PACK(struct razer_kraken_v3_request_report
{
unsigned char report_id; // usb_buf[0]
unsigned char command_id; // usb_buf[1]
unsigned char arguments[11]; // usb_buf[2...]
unsigned char arguments[13]; // usb_buf[2...]
});
class RazerKrakenV3Controller
@@ -405,7 +405,7 @@ bool RobobloqLightStripController::RequestDeviceInfo()
char uuid_buf[17];
for(int i = 0; i < 8; i++)
{
sprintf(uuid_buf + (i * 2), "%02x", data[12 + i]);
snprintf(uuid_buf + (i * 2), sizeof(uuid_buf) - (i * 2), "%02x", data[12 + i]);
}
this->uuid = std::string(uuid_buf);
@@ -102,6 +102,7 @@ REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 7700 XT Nitro+",
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 7800 XT Nitro+", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI32_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI32_7800XT_NITRO_PLUS_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 7900 GRE Nitro+", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI31_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI31_GRE_NITRO_PLUS_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 7900 XTX Nitro+", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI31_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI31_NITRO_PLUS_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 9060 XT Pure", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI44_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI44_PURE_XT_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 9060 XT Nitro+", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI48_DEV1, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI48_NITRO_PLUS_SUB_DEV1, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 9070 Pure", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI48_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI48_PURE_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
REGISTER_I2C_PCI_DETECTOR("Sapphire Radeon RX 9070 XT Nitro+", DetectSapphireV3Controllers, AMD_GPU_VEN, AMD_NAVI48_DEV, SAPPHIRE_SUB_VEN, SAPPHIRE_NAVI48_NITRO_PLUS_SUB_DEV, SAPPHIRE_NITRO_GLOW_V3_ADDR);
@@ -194,6 +194,62 @@ const keyboard_keymap_overlay_values leobog_hi75c_pro_layout
};
const keyboard_keymap_overlay_values redragon_k686_eisa_pro
{
KEYBOARD_SIZE_FULL,
{
{
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 NULL NULL NULL DEL HOME END PGUP PGDN */
0, 6, 12, 18, 24, 30, 36, 42, 48, 54, 60, 66, 72, 0, 0, 0,
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC NULL NULL NULL NMLK NMDV NMTM NMMI */
1, 7, 13, 19, 25, 31, 37, 43, 49, 55, 61, 67, 73, 79, 0, 0, 0, 91, 97, 103, 109,
/* TAB Q W E R T Y U I O P [ ] \ NULL NULL NULL NM7 NM8 NM9 NMPL */
2, 8, 14, 20, 26, 32, 38, 44, 50, 56, 62, 68, 74, 80, 0, 0, 0, 92, 98, 104, 110,
/* CPLK A S D F G H J K L ; " # ENTR NM4 NM5 NM6 */
3, 9, 15, 21, 27, 33, 39, 45, 51, 57, 63, 69, 0, 81, 93, 99, 105,
/* LSFT ISO\ Z X C V B N M , . / RSFT ARWU NM1 NM2 NM3 NMER */
4, 0, 10, 16, 22, 28, 34, 40, 46, 52, 58, 64, 82, 88, 94, 100, 106, 112,
/* LCTL LWIN LALT SPC RALT RFNC RMNU RCTL ARWL ARWD ARWR NM0 NMPD */
5, 11, 17, 35, 53, 59, 0, 65, 83, 89, 95, 101, 107,
},
{
/* Add more regional layout fixes here */
}
},
{
/*--------------------------------------------------------------------------------------------------------------------*\
| Edit Keys |
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
\*--------------------------------------------------------------------------------------------------------------------*/
{ 0, 0, 14, 78, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Replace Print w/ Delete
{ 0, 0, 15, 90, KEY_EN_INSERT, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Replace ScrLk w/ Insert
{ 0, 0, 16, 96, KEY_EN_END, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Replace Pause w/ End
{ 0, 0, 17, 102, KEY_EN_PAGE_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert PgUp
{ 0, 0, 18, 108, KEY_EN_PAGE_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert PgDn
{ 0, 2, 13, 75, KEY_EN_POUND, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Insert ] } Key
{ 0, 4, 1, 76, KEY_EN_ISO_BACK_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Insert \ | Key
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Remove Insert
{ 0, 1, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Home
{ 0, 1, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove PgUp
{ 0, 2, 1, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Padding after Tab
{ 0, 2, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Delete
{ 0, 2, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove End
{ 0, 2, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove PgDn
{ 0, 3, 1, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Padding after CapsLk
{ 0, 3, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove extra key
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove padding
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove padding
{ 0, 4, 12, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove extra key
{ 0, 4, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove padding
{ 0, 5, 12, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Menu
{ 0, 5, 16, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove padding
}
};
/*-------------------------------------------------------------------------*\
| DEVICE MODEL MAPPING |
\*-------------------------------------------------------------------------*/
@@ -210,4 +266,10 @@ const sinowealth_device_map sinowealth_10c_keyboards{
{
0xA3, { "LEOBOG Hi75C Pro", leobog_hi75c_pro_layout },
},
{
0x20, { "Redragon K686 Eisa Pro", redragon_k686_eisa_pro },
},
{
0x05, { "Redragon K686 Eisa Pro", redragon_k686_eisa_pro },
},
};
@@ -73,7 +73,13 @@ void SteelSeriesApexController::SetLEDsDirect(std::vector<RGBColor> colors)
if(use_new_protocol)
{
struct hid_device_info* info = hid_get_device_info(dev);
if(info && (info->product_id == 0x162C || info->product_id == 0x162D)) // Aparently Gen 3 wireless models reuse this protocol, make sure to place their PID here and further below when developing.
/*-------------------------------------------------*\
| Apparently Gen 3 wireless models reuse this |
| protocol, make sure to place their PID here and |
| further below when developing. |
\*-------------------------------------------------*/
if(info && (info->product_id == 0x162C || info->product_id == 0x162D))
{
packet_id = APEX_2023_PACKET_ID_DIRECT_WIRELESS;
}
@@ -112,10 +118,9 @@ void SteelSeriesApexController::SetLEDsDirect(std::vector<RGBColor> colors)
hid_send_feature_report(dev, buf, 643);
}
/*-------------------------------------------------------------------------------------------------*\
| Private packet sending functions. |
\*-------------------------------------------------------------------------------------------------*/
/*---------------------------------------------------------*\
| Private packet sending functions. |
\*---------------------------------------------------------*/
void SteelSeriesApexController::SelectProfile
(
unsigned char profile
@@ -138,35 +143,37 @@ void SteelSeriesApexController::SendInitialization()
unsigned char buf[FIRMWARE_REQ_LEN];
unsigned char read_buf[65];
int res = 0;
char version_str[32] = "Unknown";
char version_str[65] = "Unknown";
struct hid_device_info* info = hid_get_device_info(dev);
unsigned short pid = (info) ? info->product_id : 0;
// Firmware check
/*-----------------------------------------------------*\
| Firmware check |
\*-----------------------------------------------------*/
if(pid == 0x1628)
{
/*-----------------------------------------------------*\
| Zero out buffer |
\*-----------------------------------------------------*/
/*-------------------------------------------------*\
| Zero out buffer |
\*-------------------------------------------------*/
memset(buf, 0x00, sizeof(buf));
buf[0x00] = 0x00;
buf[0x01] = 0x90;
/*-----------------------------------------------------*\
| Send packet |
\*-----------------------------------------------------*/
/*-------------------------------------------------*\
| Send packet |
\*-------------------------------------------------*/
hid_write(dev, buf, 65);
/*-----------------------------------------------------*\
| Read Response |
\*-----------------------------------------------------*/
/*-------------------------------------------------*\
| Read Response |
\*-------------------------------------------------*/
memset(read_buf, 0x00, sizeof(read_buf));
res = hid_read_timeout(dev, read_buf, sizeof(read_buf), 200);
/*-----------------------------------------------------*\
| Firmware Check |
\*-----------------------------------------------------*/
/*-------------------------------------------------*\
| Firmware Check |
\*-------------------------------------------------*/
if(res > 2 && read_buf[0] == 0x90)
{
int major = 0, minor = 0, patch = 0;
@@ -178,7 +185,9 @@ void SteelSeriesApexController::SendInitialization()
if(count == 3)
{
// Currently set to 1.19.7 or newer.
/*-----------------------------------------*\
| Currently set to 1.19.7 or newer. |
\*-----------------------------------------*/
if(major > 1)
{
use_new_protocol = true;
@@ -197,7 +206,11 @@ void SteelSeriesApexController::SendInitialization()
}
}
}
// // Aparently Gen 3 models reuse this protocol, make sure to place their PID here and further above for wireless when developing.
/*-----------------------------------------------------*\
| Apparently Gen 3 models reuse this protocol, make |
| sure to place their PID here and further above for |
| wireless when developing. |
\*-----------------------------------------------------*/
else if(pid == 0x162C || pid == 0x162D)
{
use_new_protocol = true;
@@ -90,18 +90,18 @@
#define STEELSERIES_ARCTIS_5_PID 0x1250
#define STEELSERIES_ARCTIS_5_V2_PID 0x12AA
/*------------------------------------------------------------------*\
| Mousemat product IDs |
\*------------------------------------------------------------------*/
#define STEELSERIES_QCK_PRISM_CLOTH_MED_PID 0x150A
#define STEELSERIES_QCK_PRISM_CLOTH_XL_PID 0x150D
#define STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_PID 0x151E
#define STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEON_RIDER_PID 0x1514
#define STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEO_NOIR_PID 0x151C
#define STEELSERIES_QCK_PRISM_CLOTH_3XL_PID 0x1516
#define STEELSERIES_QCK_PRISM_CLOTH_4XL_PID 0x1518
#define STEELSERIES_QCK_PRISM_CLOTH_5XL_PID 0x151A
#define STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_LIGHTFALL_ED_PID 0X1520
/*--------------------------------------------------------------------*\
| Mousemat product IDs |
\*--------------------------------------------------------------------*/
#define STEELSERIES_QCK_PRISM_CLOTH_MED_PID 0x150A
#define STEELSERIES_QCK_PRISM_CLOTH_XL_PID 0x150D
#define STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_PID 0x151E
#define STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEON_RIDER_PID 0x1514
#define STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEO_NOIR_PID 0x151C
#define STEELSERIES_QCK_PRISM_CLOTH_3XL_PID 0x1516
#define STEELSERIES_QCK_PRISM_CLOTH_4XL_PID 0x1518
#define STEELSERIES_QCK_PRISM_CLOTH_5XL_PID 0x151A
#define STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_2_LIGHTFALL_ED_PID 0x1520
/*-----------------------------------------------------*\
| Keyboard product IDs |
@@ -481,18 +481,18 @@ REGISTER_HID_DETECTOR_I("SteelSeries Siberia 350", Dete
REGISTER_HID_DETECTOR_I("SteelSeries Arctis 5", DetectSteelSeriesArctis5, STEELSERIES_VID, STEELSERIES_ARCTIS_5_PID, 5 );
REGISTER_HID_DETECTOR_I("SteelSeries Arctis 5", DetectSteelSeriesArctis5, STEELSERIES_VID, STEELSERIES_ARCTIS_5_V2_PID, 5 );
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*\
| Mousemats |
\*--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth Medium", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_MED_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL Destiny Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL Destiny Lightfall Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_LIGHTFALL_ED_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL CS:GO Neon Rider Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEON_RIDER_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL CS:GO Neo Noir Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEO_NOIR_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 3XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_3XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 4XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_4XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 5XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_5XL_PID, 0 );
/*----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*\
| Mousemats |
\*----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth Medium", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_MED_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL Destiny Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL Destiny 2 Lightfall Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_DESTINY_2_LIGHTFALL_ED_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL CS:GO Neon Rider Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEON_RIDER_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth XL CS:GO Neo Noir Ed.", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_XL_CSGO_NEO_NOIR_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 3XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_3XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 4XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_4XL_PID, 0 );
REGISTER_HID_DETECTOR_I("SteelSeries QCK Prism Cloth 5XL", DetectSteelSeriesMousemat, STEELSERIES_VID, STEELSERIES_QCK_PRISM_CLOTH_5XL_PID, 0 );
/*-------------------------------------------------------------------------------------------------------------------------------------------------------------------------*\
| Keyboards |
@@ -98,7 +98,7 @@ void WootingV1KeyboardController::SendDirect(RGBColor* colors, uint8_t colour_co
unsigned char buffer3[RGB_RAW_BUFFER_SIZE] = {0};
unsigned char buffer4[RGB_RAW_BUFFER_SIZE] = {0};
for(std::size_t index = 0; index < colour_count; index++)
for(uint8_t index = 0; index < colour_count; index++)
{
unsigned char row = index / WOOTING_RGB_COLUMNS;
unsigned char col = index % WOOTING_RGB_COLUMNS;
+16
View File
@@ -123,6 +123,7 @@ const char* KEY_EN_NUMPAD_MINUS = "Key: Number Pad -";
const char* KEY_EN_NUMPAD_PLUS = "Key: Number Pad +";
const char* KEY_EN_NUMPAD_PERIOD = "Key: Number Pad .";
const char* KEY_EN_NUMPAD_ENTER = "Key: Number Pad Enter";
const char* KEY_EN_NUMPAD_EQUAL = "Key: Number Pad =";
const char* KEY_EN_NUMPAD_0 = "Key: Number Pad 0";
const char* KEY_EN_NUMPAD_1 = "Key: Number Pad 1";
const char* KEY_EN_NUMPAD_2 = "Key: Number Pad 2";
@@ -142,6 +143,19 @@ const char* KEY_EN_MEDIA_MUTE = "Key: Media Mute";
const char* KEY_EN_MEDIA_VOLUME_DOWN = "Key: Media Volume -";
const char* KEY_EN_MEDIA_VOLUME_UP = "Key: Media Volume +";
const char* KEY_EN_F13 = "Key: F13";
const char* KEY_EN_F14 = "Key: F14";
const char* KEY_EN_F15 = "Key: F15";
const char* KEY_EN_F16 = "Key: F16";
const char* KEY_EN_F17 = "Key: F17";
const char* KEY_EN_F18 = "Key: F18";
const char* KEY_EN_F19 = "Key: F19";
const char* KEY_EN_F20 = "Key: F20";
const char* KEY_EN_F21 = "Key: F21";
const char* KEY_EN_F22 = "Key: F22";
const char* KEY_EN_F23 = "Key: F23";
const char* KEY_EN_F24 = "Key: F24";
const char* KEY_JP_RO = "Key: _";
const char* KEY_JP_EJ = "Key: E/J";
const char* KEY_JP_ZENKAKU = "Key: 半角/全角";
@@ -152,6 +166,8 @@ const char* KEY_JP_YEN = "Key: ¥";
const char* KEY_JP_AT = "Key: @";
const char* KEY_JP_CHEVRON = "Key: ^";
const char* KEY_JP_COLON = "Key: :";
const char* KEY_JP_KATAKANA = "Key: カタカナ";
const char* KEY_JP_HIRAGANA = "Key: ひらがな";
const char* KEY_KR_HAN = "Key: 한/영";
const char* KEY_KR_HANJA = "Key: 한자";
+16
View File
@@ -123,6 +123,7 @@ extern const char* KEY_EN_NUMPAD_MINUS;
extern const char* KEY_EN_NUMPAD_PLUS;
extern const char* KEY_EN_NUMPAD_PERIOD;
extern const char* KEY_EN_NUMPAD_ENTER;
extern const char* KEY_EN_NUMPAD_EQUAL;
extern const char* KEY_EN_NUMPAD_0;
extern const char* KEY_EN_NUMPAD_1;
extern const char* KEY_EN_NUMPAD_2;
@@ -142,6 +143,19 @@ extern const char* KEY_EN_MEDIA_MUTE;
extern const char* KEY_EN_MEDIA_VOLUME_DOWN;
extern const char* KEY_EN_MEDIA_VOLUME_UP;
extern const char* KEY_EN_F13;
extern const char* KEY_EN_F14;
extern const char* KEY_EN_F15;
extern const char* KEY_EN_F16;
extern const char* KEY_EN_F17;
extern const char* KEY_EN_F18;
extern const char* KEY_EN_F19;
extern const char* KEY_EN_F20;
extern const char* KEY_EN_F21;
extern const char* KEY_EN_F22;
extern const char* KEY_EN_F23;
extern const char* KEY_EN_F24;
extern const char* KEY_JP_RO;
extern const char* KEY_JP_EJ;
extern const char* KEY_JP_ZENKAKU;
@@ -152,6 +166,8 @@ extern const char* KEY_JP_YEN;
extern const char* KEY_JP_AT;
extern const char* KEY_JP_CHEVRON;
extern const char* KEY_JP_COLON;
extern const char* KEY_JP_KATAKANA;
extern const char* KEY_JP_HIRAGANA;
extern const char* KEY_KR_HAN;
extern const char* KEY_KR_HANJA;
+22 -17
View File
@@ -21,11 +21,12 @@
using namespace std::chrono_literals;
// Sources for define values:
// - https://en.wikipedia.org/wiki/Serial_presence_detect
// - JEDEC DDR5 Serial Presence Detect (SPD): Table of contents
/*---------------------------------------------------------*\
| Sources for define values: |
| - https://en.wikipedia.org/wiki/Serial_presence_detect |
| - JEDEC DDR5 Serial Presence Detect (SPD): Table of |
| contents |
\*---------------------------------------------------------*/
#define BASIC_MEMORY_TYPE_ADDR (0x02)
#define DDR4_JEDEC_ID_ADDR (0x140)
@@ -115,23 +116,27 @@ std::string SPDAccessor::read_part_nr_at(uint16_t address, std::size_t len)
{
std::string part_number;
for(std::size_t i = 0; i < len; i++)
for(uint16_t i = 0; i < (uint16_t)len; i++)
{
std::size_t spd_addr = address + i;
uint16_t spd_addr = address + i;
part_number += (char)this->at(spd_addr);
}
// Find the true end of string & truncate it to that point.
// Part number should be padded with 0x20 (space) for DDR4 (Source: Wikipedia)
// It may be padded with 0x00 (Source: real-life tests on DDR5 memory)
// Note: To prevent infinite loop, end_of_string_idx MUST be signed.
int end_of_string_idx = part_number.length()-1;
for(; end_of_string_idx >= 0; end_of_string_idx--)
/*-----------------------------------------------------*\
| Find the true end of string and truncate it to that |
| point. Part number should be padded with 0x20 |
| (space) for DDR4 (Source: Wikipedia). |
| It may be padded with 0x00 (Source: real-life tests |
| on DDR5 memory). |
| Note: To prevent infinite loop, end_of_string_idx |
| MUST be signed. |
\*-----------------------------------------------------*/
std::size_t end_of_string_idx = part_number.length();
for(; end_of_string_idx > 0; end_of_string_idx--)
{
if(
part_number[end_of_string_idx] != '\0' &&
part_number[end_of_string_idx] != ' '
)
if((part_number[end_of_string_idx - 1] != '\0')
&& (part_number[end_of_string_idx - 1] != ' '))
{
break;
}
+17 -17
View File
@@ -13,96 +13,96 @@ typedef void * (*nvapi_QueryInterface_t)(int);
// Constructors for NvAPI structures that just zero the memory and set the right version
NV_DELTA_ENTRY::NV_DELTA_ENTRY()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
}
NV_GPU_PSTATES20_V2::NV_GPU_PSTATES20_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_PSTATES20_V2, 2);
}
NV_CLOCK_FREQUENCIES_V2::NV_CLOCK_FREQUENCIES_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_CLOCK_FREQUENCIES_V2, 2);
}
NV_GPU_PERFORMANCE_TABLE_V1::NV_GPU_PERFORMANCE_TABLE_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_PERFORMANCE_TABLE_V1, 1);
}
NV_DYNAMIC_PSTATES_V1::NV_DYNAMIC_PSTATES_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_DYNAMIC_PSTATES_V1, 1);
}
NV_GPU_POWER_POLICIES_INFO_V1::NV_GPU_POWER_POLICIES_INFO_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_POWER_POLICIES_INFO_V1, 1);
}
NV_GPU_POWER_POLICIES_STATUS_V1::NV_GPU_POWER_POLICIES_STATUS_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_POWER_POLICIES_STATUS_V1, 1);
}
NV_GPU_VOLTAGE_DOMAINS_STATUS_V1::NV_GPU_VOLTAGE_DOMAINS_STATUS_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_VOLTAGE_DOMAINS_STATUS_V1, 1);
}
NV_GPU_THERMAL_SETTINGS_V2::NV_GPU_THERMAL_SETTINGS_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_THERMAL_SETTINGS_V2, 2);
}
NV_GPU_THERMAL_POLICIES_INFO_V2::NV_GPU_THERMAL_POLICIES_INFO_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_THERMAL_POLICIES_INFO_V2, 2);
}
NV_GPU_THERMAL_POLICIES_STATUS_V2::NV_GPU_THERMAL_POLICIES_STATUS_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_THERMAL_POLICIES_STATUS_V2, 2);
}
NV_GPU_COOLER_SETTINGS_V2::NV_GPU_COOLER_SETTINGS_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_COOLER_SETTINGS_V2, 2);
}
NV_GPU_COOLER_LEVELS_V1::NV_GPU_COOLER_LEVELS_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_GPU_COOLER_LEVELS_V1, 1);
}
NV_MEMORY_INFO_V2::NV_MEMORY_INFO_V2()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_MEMORY_INFO_V2, 2);
}
NV_DISPLAY_DRIVER_VERSION_V1::NV_DISPLAY_DRIVER_VERSION_V1()
{
memset(this, 0, sizeof *this);
memset((void*)this, 0, sizeof *this);
version = NV_STRUCT_VERSION(NV_DISPLAY_DRIVER_VERSION_V1, 1);
}
NV_I2C_INFO_V3::NV_I2C_INFO_V3()
{
memset(this, 0, sizeof * this);
memset((void*)this, 0, sizeof * this);
version = NV_STRUCT_VERSION(NV_I2C_INFO_V3, 3);
}
@@ -268,7 +268,7 @@ static bool QueryInterfaceOpaque(nvapi_QueryInterface_t query_interface, NV_U32
template<typename F>
static void QueryInterfaceCast(nvapi_QueryInterface_t query_interface, NV_U32 id, const char */*function_name*/, F &function_pointer)
{
const bool result = QueryInterfaceOpaque(query_interface, id, (void **)&function_pointer);
/*const bool result = */QueryInterfaceOpaque(query_interface, id, (void **)&function_pointer);
////Log::write("%s querying interface '0x%08x' '%s'", result ? "success" : "failure", id, function_name);
}
+5
View File
@@ -791,6 +791,7 @@
#define MSI_RTX3090TI_SUPRIM_X_SUB_DEV 0x5090
#define MSI_RTX3090TI_GAMING_X_TRIO_SUB_DEV 0x5091
#define MSI_RTX4060_GAMING_X_8G_SUB_DEV 0x5160
#define MSI_RTX4060_GAMING_X_NV_EDITION_8G_SUB_DEV 0x5164
#define MSI_RTX4060TI_GAMING_X_8G_SUB_DEV 0x5152
#define MSI_RTX4060TI_GAMING_X_16G_SLIM_WHITE_SUB_DEV 0x5171
#define MSI_RTX4060TI_GAMING_X_16G_SUB_DEV 0x5172
@@ -815,6 +816,7 @@
#define MSI_RTX4090_SUPRIM_LIQUID_X_SUB_DEV 0x5104
#define MSI_RTX4090_SUPRIM_X_SUB_DEV 0x5102
#define MSI_RTX5070TI_GAMING_TRIO_SUB_DEV 0x5315
#define MSI_RTX5070TI_VANGUARD_SOC_SUB_DEV 0X5314
#define MSI_RTX5080_GAMING_TRIO_OC_SUB_DEV 0x5315
#define MSI_RTX5080_VANGUARD_SOC_SUB_DEV 0x5314
#define MSI_RTX5080_SUPRIM_SOC_SUB_DEV 0x5313
@@ -861,6 +863,7 @@
#define PNY_RTX_4090_XLR8_VERTO_SUB_DEV 0x13AE
#define PNY_RTX_4090_VERTO_EPIC_X_SUB_DEV 0x13D8
#define PNY_RTX_4090_VERTO_EPIC_X_OC_SUB_DEV 0x13D9
#define PNY_RTX_5070_ARGB_EPIC_X_OC_SUB_DEV 0x1439
#define PNY_RTX_5070TI_ARGB_EPIC_X_OC_SUB_DEV 0x143A
#define PNY_RTX_5080_ARGB_EPIC_X_OC_SUB_DEV 0x1435
#define PNY_RTX_5090_ARGB_EPIC_X_OC_SUB_DEV 0x1446
@@ -895,6 +898,7 @@
#define PALIT_RTX5070_GAMINGPRO_SUB_DEV 0xF324
#define PALIT_RTX5070TI_GAMEROCK_SUB_DEV 0xF320
#define PALIT_RTX5070TI_GAMINGPRO_SUB_DEV 0xF322
#define PALIT_RTX5070TI_GAMINGPRO_S_SUB_DEV 0xF332
#define PALIT_RTX5080_GAMEROCK_SUB_DEV 0xF320
#define PALIT_RTX5080_GAMINGPRO_SUB_DEV 0xF322
#define PALIT_RTX5090_GAMEROCK_SUB_DEV 0xF318
@@ -943,6 +947,7 @@
#define SAPPHIRE_NAVI21_TOXIC_SUB_DEV 0xF440
#define SAPPHIRE_NAVI21_TOXIC_SUB_DEV1 0xF441
#define SAPPHIRE_NAVI31_NITRO_PLUS_SUB_DEV 0xE471
#define SAPPHIRE_NAVI44_PURE_XT_SUB_DEV 0x493E
#define SAPPHIRE_NAVI48_NITRO_PLUS_SUB_DEV 0xE489
#define SAPPHIRE_NAVI48_NITRO_PLUS_SUB_DEV1 0xE493
#define SAPPHIRE_NAVI48_PURE_SUB_DEV 0x4499
+17 -2
View File
@@ -139,9 +139,24 @@ OpenRGBSettingsPage::OpenRGBSettingsPage(QWidget *parent) :
}
}
/*-------------------------------------*\
| Use PascalCase key for compatibility |
| should be removed later on. |
\*-------------------------------------*/
if(ui_settings.contains("RunZoneChecks"))
{
ui->CheckboxRunZoneChecks->setChecked(ui_settings["RunZoneChecks"]);
/*----------------------------------*\
| Migrate key to snake_case version |
\*----------------------------------*/
ui_settings["run_zone_checks"] = ui_settings["RunZoneChecks"];
ui_settings.erase("RunZoneChecks");
ResourceManager::get()->GetSettingsManager()->SetSettings("UserInterface", ui_settings);
ui->CheckboxRunZoneChecks->setChecked(ui_settings["run_zone_checks"]);
}
else if (ui_settings.contains("run_zone_checks"))
{
ui->CheckboxRunZoneChecks->setChecked(ui_settings["run_zone_checks"]);
}
else
{
@@ -579,7 +594,7 @@ void OpenRGBSettingsPage::on_CheckboxSaveGeometry_clicked()
void OpenRGBSettingsPage::on_CheckboxRunZoneChecks_clicked()
{
json ui_settings = ResourceManager::get()->GetSettingsManager()->GetSettings("UserInterface");
ui_settings["RunZoneChecks"] = ui->CheckboxRunZoneChecks->isChecked();
ui_settings["run_zone_checks"] = ui->CheckboxRunZoneChecks->isChecked();
ResourceManager::get()->GetSettingsManager()->SetSettings("UserInterface", ui_settings);
SaveSettings();
}
@@ -27,9 +27,9 @@ void OpenRGBZonesBulkResizer::RunChecks(QWidget *parent)
SettingsManager* settings_manager = ResourceManager::get()->GetSettingsManager();
json ui_settings = settings_manager->GetSettings("UserInterface");
if(!ui_settings.is_null() && ui_settings.contains("RunZoneChecks"))
if(!ui_settings.is_null() && ui_settings.contains("run_zone_checks"))
{
json run_zone_checks = ui_settings["RunZoneChecks"];
json run_zone_checks = ui_settings["run_zone_checks"];
if(!run_zone_checks.is_null() && run_zone_checks.is_boolean())
{
@@ -233,7 +233,7 @@ void OpenRGBZonesBulkResizer::SaveDoNotRunState()
bool state = ui->do_not_show_again_checkbox->checkState() == Qt::Checked;
ui_settings["RunZoneChecks"] = !state;
ui_settings["run_zone_checks"] = !state;
settings_manager->SetSettings("UserInterface", ui_settings);
settings_manager->SaveSettings();
+1 -1
View File
@@ -154,7 +154,7 @@ void Swatches::drawSwatches(const QSize &newSize)
/*-----------------------------------------------------*\
| Paint the swatch cluster |
\*-----------------------------------------------------*/
int width = qMin(width_inc_margin, (newSize.width() / minColumns) - (margin * 2));
int width = (newSize.width() / minColumns) - (margin * 2);
int height = minSize;
width_inc_margin = width + (margin * 2);
height_inc_margin = height + (margin * 2);
@@ -65,6 +65,14 @@ std::vector<std::string *> find_usb_serial_port(unsigned short vid, unsigned sho
| readlink() does not null-terminate, so manually terminate it |
\*-----------------------------------------------------------------*/
ssize_t link_path_size = readlink(tty_path, symlink_path, 1024);
if(link_path_size < 0 || link_path_size >= 1024)
{
/*-----------------------------------------------------------------*\
| readlink failed or buffer too small, skip this device |
\*-----------------------------------------------------------------*/
ent = readdir(dir);
continue;
}
symlink_path[link_path_size] = '\0';
char * usb_string = strstr(symlink_path, "usb");
+5 -3
View File
@@ -62,10 +62,12 @@ int startup(int argc, char* argv[], unsigned int ret_flags)
LOG_TRACE("[main] initializing GUI");
/*-------------------------------------------------*\
| Enable high DPI scaling support |
| Enable high DPI scaling support (Qt5 only) |
\*-------------------------------------------------*/
QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps, true);
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling, true);
#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps, true);
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling, true);
#endif
/*-------------------------------------------------*\
| Enable high DPI fractional scaling support on |