Automatic 'login' script
Forum rules
Only post additional bot resources here. Please do not ask unrelated questions.
Only post additional bot resources here. Please do not ask unrelated questions.
Re: Automatic 'login' script
There is a race condition in the window reservation which results in random login failures, particularly when starting multiple windows simultaneously.
This is due to the reserveActiveWindow() using a "check file" loop followed by a make file which is absolutely not atomic, ie two logins can compete for the lock. Although it sounds like a rare condition I get into it approx every 3rd time starting my 6 client script.
I would recommend using the mkdir command instead, this is atomic.
So loop on mkdir, if successful u got the lock, else loop again with appropriate timeout of course, The dead process test can be done by checking the creation time of the directory, pretty much same as done w. the file today.
Just my 5 cents
Best regards
DX
This is due to the reserveActiveWindow() using a "check file" loop followed by a make file which is absolutely not atomic, ie two logins can compete for the lock. Although it sounds like a rare condition I get into it approx every 3rd time starting my 6 client script.
I would recommend using the mkdir command instead, this is atomic.
So loop on mkdir, if successful u got the lock, else loop again with appropriate timeout of course, The dead process test can be done by checking the creation time of the directory, pretty much same as done w. the file today.
Just my 5 cents
Best regards
DX
Re: Automatic 'login' script
If you are having problems then I welcome your feedback as I didn't get to stress test it.
I think I understand what you are saying. If 2 MMs exit the loop at the same time then one will succeed and the other will fail. I assumed that if 1 starts writing to the file that it would somehow become locked to other processes writing to it, but I just checked, 2 MMs can be writing to the file at the same time. So something has to be done to make it more reliable.
I'm not sure how mkdir comes into it. How would you record which MM has the active control? How do you read the creation time of a file from MM?
The idea I had was, after it writes to the file it reads it, maybe after a small pause. If it still has control then it continues. If another processes pid is recorded then it returns to the loop to wait again.
What do you think?
I think I understand what you are saying. If 2 MMs exit the loop at the same time then one will succeed and the other will fail. I assumed that if 1 starts writing to the file that it would somehow become locked to other processes writing to it, but I just checked, 2 MMs can be writing to the file at the same time. So something has to be done to make it more reliable.
I'm not sure how mkdir comes into it. How would you record which MM has the active control? How do you read the creation time of a file from MM?
The idea I had was, after it writes to the file it reads it, maybe after a small pause. If it still has control then it continues. If another processes pid is recorded then it returns to the loop to wait again.
What do you think?
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
No matter how u twist and turn it u cant make a locking mechanism in Lua file module, its simply not atomic and u will get race condition, u can make the chances small but not remove them totally. The mkdir/rmdir Windows commands (and underlying api) are atomic on the other hand, they either fail or complete and return code indicates state so we can use them for making a locking mechanisms without race conditions.
Since lua doesnt have much of a "check attributes of files and directories" api (except in lfs) we need to keep your timeout mechanism with a separate file for overriding the lock in case of stale locks.
I also modified the backoff rest to be random for more gracefully backoff.
I typically use Lua module lfs for this but thats not a good idea here as its an external "c" module, so attached is my suggestion. I've tested it as far as I can with servers down
regards
dx
EDIT: Damn, the timeout mechanism will still have a race, what if we read the timeout file, find it stale and remove it, but in between another process has done the same - then we have a race. So, the timeout file should have a separate lock i guess..which again opens up for deadlocks lol
EDIT: Ops forgot to make the timeout file....
Since lua doesnt have much of a "check attributes of files and directories" api (except in lfs) we need to keep your timeout mechanism with a separate file for overriding the lock in case of stale locks.
I also modified the backoff rest to be random for more gracefully backoff.
I typically use Lua module lfs for this but thats not a good idea here as its an external "c" module, so attached is my suggestion. I've tested it as far as I can with servers down
regards
dx
EDIT: Damn, the timeout mechanism will still have a race, what if we read the timeout file, find it stale and remove it, but in between another process has done the same - then we have a race. So, the timeout file should have a separate lock i guess..which again opens up for deadlocks lol
EDIT: Ops forgot to make the timeout file....
Code: Select all
local function lockdir(lockPath)
return os.execute("mkdir "..string.fixPath(lockPath, false).." 2> nul")
end
local function unlockdir(lockPath)
os.execute("rmdir "..string.fixPath(lockPath, false))
end
local function reserveActiveWindow()
local lockPath = getExecutionPath().."/../micromacro.lck"
local lock = lockdir(lockPath)
-- Wait for if other bot needs active window
local printed = false
while lock ~= 0 do
file = io.open(getExecutionPath().."/../micromacro.pid", "r");
if file then
raw = file:read() or ""
file:close()
apid, atime = string.match(raw,"pid:(.*) time:(.*)")
apid = tonumber(apid)
atime = tonumber(atime)
if apid == nil or apid == pid or os.time()-tonumber(atime) > 60 then
releaseActiveWindow()
else
if not printed then
printf("Waiting for another bot to release the active window.")
printed = true
else
printf(".")
end
end
end
yrest(math.random(3000))
lock = lockdir(lockPath)
end
if printed then printf("\n") end
end
local function releaseActiveWindow()
os.remove(getExecutionPath().."/../micromacro.pid")
unlockdir(getExecutionPath().."/../micromacro.lck")
end
Re: Automatic 'login' script
New locking, take 2
-dx
-dx
Code: Select all
local function lockdir(lockPath)
return (os.execute("mkdir "..string.fixPath(lockPath, false).." 2> nul") == 0)
end
local function unlockdir(lockPath)
os.execute("rmdir "..string.fixPath(lockPath, false))
end
local function setTimeout(pidPath)
file, err = io.open(pidPath, "w");
if( not file ) then
error(err, 0);
end
file:write("pid:"..getHwnd().." time:"..os.time())
file:close()
end
local function getTimeout(pidPath)
file = io.open(pidPath, "r");
if file then
raw = file:read() or ""
file:close()
apid, atime = string.match(raw,"pid:(.*) time:(.*)")
apid = tonumber(apid)
atime = tonumber(atime)
if apid and atime then
return apid, atime
end
end
return nil, nil
end
local function releaseActiveWindow()
os.remove(getExecutionPath().."/../micromacro.pid")
unlockdir(getExecutionPath().."/../micromacro.lck")
end
local function reserveActiveWindow()
local lockPath = getExecutionPath().."/../micromacro.lck"
local pidPath = getExecutionPath().."/../micromacro.pid"
local lock = lockdir(lockPath)
local pid = getHwnd()
-- Wait for if other bot needs active window
local printed = false
while not lock do
local atime, atime = getTimeout(pidPath)
-- If nil, we prolly interupted another process between creating and writing
if apid and atime then
if apid == pid or os.time()-tonumber(atime) > 60 then
printf("\nLock stale, cleaning up.")
releaseActiveWindow()
else
if not printed then
printf("Waiting for another bot to release the active window.")
printed = true
else
printf(".")
end
end
end
yrest(math.random(3000))
lock = lockdir(lockPath)
end
if printed then printf("\n") end
-- Timestamp the active window
setTimeout(pidPath)
end
Re: Automatic 'login' script
I was testing the mkdir command. It returns 3 values. The first one is nil or true. It never equals 0 so the locking function always returns false. I wonder if the returned values might depend on the system. Also the directory name needs to be surrounded by quotes for paths with spaces.
This worked for me.
Successfully created the directory.
Directory already exists so failed
If we can rely on only one process creating the folder do we even need the pid file? Or maybe we do, to check the age.
This worked for me.
Successfully created the directory.
Code: Select all
Command> print(os.execute("mkdir \""..string.fixPath(getExecutionPath().."/../mi
cromacro.lck\"", false).." 2> nul") == true)
true
Code: Select all
Command> print(os.execute("mkdir \""..string.fixPath(getExecutionPath().."/../mi
cromacro.lck\"", false).." 2> nul") == true)
false
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
Well, the lock might be stale if a process gets killed while holding the lock, its a rare event but might happen. Another way would be to put in a timer and remove lock if its not gone in 60s, assuming all multi-login sequences will be faster than that. Assuming a login uses 10s this leaves room for 6 client logins, ppl who do more prolly know enough to increase the limit.
The return value was different, I get as below. Im using Windows7 64b and Lua 5.1 (5.2 missing so much support for extensions)
The return value was different, I get as below. Im using Windows7 64b and Lua 5.1 (5.2 missing so much support for extensions)
-dxCommand> print(os.execute("mkdir tt"))
0
Command> print(os.execute("mkdir tt"))
A subdirectory or file tt already exists.
1
Command> print(type(os.execute("mkdir tt")))
number
Command>
Re: Automatic 'login' script
Here are my exact same commands.
I'm using 5.2 though. I don't know if something changed in MM.
Just found and old version of 1.04. The display is the same as yours.
It would definitely have to support the latest MM. We could easily support both by doing.
Code: Select all
Command> print(os.execute("mkdir tt"))
true exit 0
Command> print(os.execute("mkdir tt"))
A subdirectory or file tt already exists.
nil exit 1
Command> print(type(os.execute("mkdir tt")))
A subdirectory or file tt already exists.
nil
Just found and old version of 1.04. The display is the same as yours.
It would definitely have to support the latest MM. We could easily support both by doing.
Code: Select all
local function lockdir(lockPath)
local code = os.execute("mkdir \""..string.fixPath(lockPath, false).."\" 2> nul")
return (code == 0 or code == true)
end
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
Agree, need support for both versions.
-dx
-dx
Re: Automatic 'login' script
Hello,
I always get stuck while it should select the char (1-8). I figured out that the function gameState returns 0 instead of 2.
I always get stuck while it should select the char (1-8). I figured out that the function gameState returns 0 instead of 2.
-
- Posts: 446
- Joined: Wed Aug 03, 2011 7:37 pm
Re: Automatic 'login' script
you didnt happen to disable the zoom that happens when you get to the character selection screen did you? from memory there is a setting in one of the interface/login/*.lua files to do this. when it is set, the gameState returns 0 instead of 2C3PO wrote:Hello,
I always get stuck while it should select the char (1-8). I figured out that the function gameState returns 0 instead of 2.
Re: Automatic 'login' script
I'm not sure if I understand what you mean ...
Should I set fastLoginNoZoom to false? is it that what you wanted to tell me?
Should I set fastLoginNoZoom to false? is it that what you wanted to tell me?
Re: Automatic 'login' script
That's what he meant, yes. It needs to zoom in. This was reported before. I don't think I came up with fix for it. It shouldn't be a problem though, it zooms in pretty quickly.
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
oh its not a problem, if I know that I can disable it again.
thx for the fast replies
thx for the fast replies
Re: Automatic 'login' script
Hi, it's me again
I have 2 questions:
I have 2 questions:
- is it possible to minimize the rom-window within the wp-script?
is it possible to close all windows, or better to end the processes (MM and RoM)
Re: Automatic 'login' script
C3PO wrote:minimize the rom-window within the wp-script?
Code: Select all
showWindow(getWin(), sw.minimize);
Do you mean minimize all games? You would have to search for the other clients that the current bot is not attached to.C3PO wrote:is it possible to close all windows
Code: Select all
windows = findWindowList("*", "Radiant Arcana")
for k,window in pairs(windows) do
showWindow(window, sw.minimize);
end
TASKKILL works well enoughC3PO wrote:or better to end the processes (MM and RoM)
Code: Select all
pid = findProcessByWindow(window)
os.execute("TASKKILL /PID " .. pid .. " /F")
Code: Select all
windows = findWindowList("*", "ConsoleWindowClass") -- Note this will match Window command consoles too.
for k,window in pairs(windows) do
if window ~= getHwnd() -- Does not equal current mm window
pid = findProcessByWindow(window)
os.execute("TASKKILL /PID " .. pid .. " /F")
end
end
-- end current mm window
pid = findProcessByWindow(getHwnd())
os.execute("TASKKILL /PID " .. pid .. " /F")
For more information check out the 'process' section of the micromacro wiki.
http://www.solarstrike.net/wiki/index.php5?title=Manual
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
Hello,
I've got another problem... From time to time the script hangs up because the Choose Server Frame is displayed. Am I doing something wrong or is there a solution for that ...
I've got another problem... From time to time the script hangs up because the Choose Server Frame is displayed. Am I doing something wrong or is there a solution for that ...
Re: Automatic 'login' script
The latest version of fastlogin fises that. Try updating.
- Please consider making a small donation to me to support my continued contributions to the bot and this forum. Thank you. Donate
- I check all posts before reading PMs. So if you want a fast reply, don't PM me but post a topic instead. PM me for private or personal topics only.
- How to: copy and paste in micromacro
________________________
Quote:- “They say hard work never hurt anybody, but I figure, why take the chance.”
- Ronald Reagan
Re: Automatic 'login' script
Hi Rock5 (long time no see!)
I successfully setup your fast login (108 char version) and bot is running as intendend (no error from the first to the last character in the account).
Also successfully setup this automatic login script; from micromacro window with the following string bot run with no error:
But when i try to make a bat file tier2.bat with the following code: micromacro give me the error in the attached image.
I'm sure i'm mistaking the sintax, but i can't found the right one, can you give it a look and tell me in what i'm wrong?
thx
I successfully setup your fast login (108 char version) and bot is running as intendend (no error from the first to the last character in the account).
Also successfully setup this automatic login script; from micromacro window with the following string bot run with no error:
Code: Select all
rom/login acc:1 char:1 path:tier2
Code: Select all
START micromacro.exe scripts\rom\login acc:1 char:1 path:tier2
I'm sure i'm mistaking the sintax, but i can't found the right one, can you give it a look and tell me in what i'm wrong?
thx
Re: Automatic 'login' script
As rock5 said in first post
so in your case batch file would berock5 wrote: Examples:
- From the Micromacro console
Code: Select all
rom/login acc:48 char:2 client:rom4u path:cot_tele
- Or starting multiple clients from a batch file
Code: Select all
FOR /F "tokens=1 delims=" %%A in ('cd') do SET folder=%%A START ../../micromacro.exe "%folder%/login.lua" acc:45 char:1 client:rom4u path:path1 START ../../micromacro.exe "%folder%/login.lua" acc:46 char:1 client:rom4u path:path2 START ../../micromacro.exe "%folder%/login.lua" acc:47 char:1 client:rom4u path:path3
Code: Select all
FOR /F "tokens=1 delims=" %%A in ('cd') do SET folder=%%A
START ../../micromacro.exe "%folder%/login.lua" acc:1 char:1 client:rom path:tier2
Life is a journey, not destination
Re: Automatic 'login' script
I have 2 runes of magic clients. One for manual play and one with ultra model files. This works great when I'm starting the clients manually and then start the bot but weird things happen when I try to do it with login script.
Even if the ultra model files are not installed on my manual client, when I start it with the bot it starts without textures anyways. When I start it manually it works though. I have checked the shortcuts and they are correct. When I start my model client for manual play and then start the non-model client with the bot the textures works. So somehow the bot manages to start a client with model files that doesn't exist in that folder.
Also any time I start a client with the bot the settings in game resets. As example it always changes graphics from low to medium.
The clients are installed in C:\Program Files\Runes of Magic\Client.exe and C:\Program Files (x86)\Runes Of Magic\Client.exe
Even if the ultra model files are not installed on my manual client, when I start it with the bot it starts without textures anyways. When I start it manually it works though. I have checked the shortcuts and they are correct. When I start my model client for manual play and then start the non-model client with the bot the textures works. So somehow the bot manages to start a client with model files that doesn't exist in that folder.
Also any time I start a client with the bot the settings in game resets. As example it always changes graphics from low to medium.
The clients are installed in C:\Program Files\Runes of Magic\Client.exe and C:\Program Files (x86)\Runes Of Magic\Client.exe
Here is my gathering waypoints: http://solarstrike.net/phpBB3/viewtopic.php?f=27&t=3603
Who is online
Users browsing this forum: No registered users and 0 guests