2323#include < tlhelp32.h>
2424#include < psapi.h>
2525#include < mutex>
26+ #include < atomic>
2627
2728#pragma comment(lib, "ws2_32.lib")
2829#pragma comment(lib, "shlwapi.lib")
@@ -66,6 +67,7 @@ struct AccountConfig {
6667struct GlobalConfig {
6768 int delay;
6869 bool POLProxy;
70+ std::string clientRegion; // "US" or "JP"
6971 std::vector<AccountConfig> accounts;
7072};
7173
@@ -337,6 +339,7 @@ std::string readConfigFile(const std::string& path) {
337339void writeConfigFile (const std::string& path, const GlobalConfig& config) {
338340 json j;
339341 j[" delay" ] = config.delay ;
342+ j[" clientRegion" ] = config.clientRegion ;
340343 json accounts = json::array ();
341344 for (const auto & account : config.accounts ) {
342345 json acc;
@@ -356,12 +359,14 @@ GlobalConfig loadConfig(const std::string& path) {
356359 GlobalConfig config;
357360 std::string content = readConfigFile (path);
358361 if (content.empty ()) {
362+ config.clientRegion = " US" ; // Default to US
359363 return config;
360364 }
361365 try {
362366 json j = json::parse (content);
363367 config.delay = j.value (" delay" , 3000 );
364368 config.POLProxy = true ;
369+ config.clientRegion = j.value (" clientRegion" , " US" ); // Default to US if not set
365370 if (j.contains (" accounts" )) {
366371 for (const auto & acc : j[" accounts" ]) {
367372 AccountConfig account;
@@ -375,13 +380,31 @@ GlobalConfig loadConfig(const std::string& path) {
375380 }
376381 } catch (const std::exception& e) {
377382 std::cerr << " Error parsing config file: " << e.what () << std::endl;
383+ config.clientRegion = " US" ; // Default to US on error
378384 }
379385 return config;
380386}
381387
382388void setupConfig (GlobalConfig& config) {
383389 std::cout << " Setting up FFXI autoPOL configuration\n " ;
384390 std::string input;
391+
392+ // Client region selection
393+ while (true ) {
394+ std::cout << " Client region (US/JP, default US): " ;
395+ std::getline (std::cin, input);
396+ if (input.empty ()) {
397+ config.clientRegion = " US" ;
398+ break ;
399+ }
400+ std::transform (input.begin (), input.end (), input.begin (), ::toupper);
401+ if (input == " US" || input == " JP" ) {
402+ config.clientRegion = input;
403+ break ;
404+ }
405+ std::cout << " Please enter 'US' or 'JP'.\n " ;
406+ }
407+
385408 std::cout << " Delay before input starts (in seconds, default 3): " ;
386409 std::getline (std::cin, input);
387410 if (input.empty ()) {
@@ -529,6 +552,9 @@ void defocusExistingPOL() {
529552}
530553
531554void launchAccount (const AccountConfig& account, const GlobalConfig& config) {
555+ // Determine port based on client region
556+ int port = (config.clientRegion == " JP" ) ? 51300 : 51304 ;
557+
532558 // Check if the port can be opened
533559 SOCKET testSocket = socket (AF_INET , SOCK_STREAM , IPPROTO_TCP );
534560 bool portAvailable = false ;
@@ -538,7 +564,7 @@ void launchAccount(const AccountConfig& account, const GlobalConfig& config) {
538564 sockaddr_in serverAddr;
539565 serverAddr.sin_family = AF_INET ;
540566 inet_pton (AF_INET , " 127.0.0.1" , &serverAddr.sin_addr );
541- serverAddr.sin_port = htons (51304 );
567+ serverAddr.sin_port = htons (port );
542568
543569 // Set socket options before bind
544570 int opt = 1 ;
@@ -552,7 +578,7 @@ void launchAccount(const AccountConfig& account, const GlobalConfig& config) {
552578 } else {
553579 if (bind (testSocket, (sockaddr*)&serverAddr, sizeof (serverAddr)) == SOCKET_ERROR ) {
554580 DWORD error = WSAGetLastError ();
555- std::cerr << " POL Redirect won't work: Port 51304 is already in use (Error: " << error << " )\n " ;
581+ std::cerr << " POL Redirect won't work: Port " << port << " is already in use (Error: " << error << " )\n " ;
556582 } else {
557583 portAvailable = true ;
558584 if (config.POLProxy ) {
@@ -798,6 +824,9 @@ void launchAccount(const AccountConfig& account, const GlobalConfig& config) {
798824
799825std::atomic<bool > shouldExit (false );
800826
827+ // Global variable to store the port for the proxy server
828+ std::atomic<int > proxyPort (51304 );
829+
801830void startProxyServer () {
802831 WSADATA wsaData;
803832 if (WSAStartup (MAKEWORD (2 , 2 ), &wsaData) != 0 ) {
@@ -833,7 +862,7 @@ void startProxyServer() {
833862 sockaddr_in serverAddr;
834863 serverAddr.sin_family = AF_INET ;
835864 inet_pton (AF_INET , " 127.0.0.1" , &serverAddr.sin_addr );
836- serverAddr.sin_port = htons (51304 );
865+ serverAddr.sin_port = htons (proxyPort. load () );
837866
838867 if (bind (serverSocket, (sockaddr*)&serverAddr, sizeof (serverAddr)) == SOCKET_ERROR ) {
839868 DWORD error = WSAGetLastError ();
@@ -907,6 +936,7 @@ bool editConfig(GlobalConfig& config) {
907936 std::cout << " [A] Add new character\n " ;
908937 std::cout << " [D] Delete character\n " ;
909938 std::cout << " [C] Modify timeout\n " ;
939+ std::cout << " [R] Change client region (US/JP)\n " ;
910940 std::cout << " [X] Exit to selection screen\n " ;
911941 std::cout << " Enter option: " ;
912942 std::getline (std::cin, input);
@@ -1018,6 +1048,17 @@ bool editConfig(GlobalConfig& config) {
10181048 std::cout << " Timeout updated.\n " ;
10191049 }
10201050 }
1051+ } else if (input == " r" ) {
1052+ std::cout << " Current client region: " << config.clientRegion << " \n " ;
1053+ std::cout << " New client region (US/JP): " ;
1054+ std::getline (std::cin, input);
1055+ std::transform (input.begin (), input.end (), input.begin (), ::toupper);
1056+ if (input == " US" || input == " JP" ) {
1057+ config.clientRegion = input;
1058+ std::cout << " Client region updated to " << config.clientRegion << " .\n " ;
1059+ } else {
1060+ std::cout << " Invalid region. Please enter 'US' or 'JP'.\n " ;
1061+ }
10211062 } else if (input == " x" ) {
10221063 return false ; // Return to selection screen
10231064 } else {
@@ -1059,7 +1100,7 @@ void removeHostsEntry() {
10591100// Update main to remove hosts entry before exiting
10601101int main (int argc, char * argv[]) {
10611102 std::cout << " Created by: jaku | https://twitter.com/jaku\n " ;
1062- std::cout << " Version: 0.0.19 | https://github.com/jaku/FFXI-autoPOL\n " ;
1103+ std::cout << " Version: 0.0.20 | https://github.com/jaku/FFXI-autoPOL\n " ;
10631104 DEBUG_KEY_PRESSES = false ;
10641105 // Parse command line arguments
10651106 for (int i = 1 ; i < argc; i++) {
@@ -1151,6 +1192,9 @@ int main(int argc, char* argv[]) {
11511192 continue ; // Go back to selection if editConfig returned
11521193 }
11531194 }
1195+ // Set proxy port based on client region
1196+ proxyPort = (config.clientRegion == " JP" ) ? 51300 : 51304 ;
1197+
11541198 // Always start proxy server
11551199 std::thread proxyThread (startProxyServer);
11561200 // Find the account to launch
0 commit comments