SeekToBegin fails when running as LocalSystem - c++

The snippet of code below is used to download a file from a remote server. It works fine when run as a user or as an administrator but returns an error when run as LocalSystem (the requested operation is invalid). When we comment out the line fSourceFile->SeekToBegin(); the programs runs fine as LocalSystem.
Any insights into why we are getting this error? Should we worry about removing the statement: fSourceFile->SeekToBegin(); Any alternate approaches?
fSourceFile = (CHttpFile*)netSession.OpenURL(pwnd->m_strSource,1,
INTERNET_FLAG_TRANSFER_BINARY | INTERNET_FLAG_RELOAD);
// Get the starting time of the download(kb/sec calculation)
COleDateTime dlStart = COleDateTime::GetCurrentTime();
fSourceFile->SeekToBegin(); // Move cursor back to top for reading*/

Related

AWS Lambda download a file using Chromedriver

I have a container that is built to run selenium-chromedriver with python to download an excel(.xlsx) file from a website.
I am Using SAM to build & deploy this image to be run in AWS Lambda.
When I build the container and invoke it locally, the program executes as expected: The download occurs and I can see the file placed in the root directory of the container.
The problem is: when I deploy this image to AWS and invoke my lambda function I get no errors, however, my download is never executed. The file never appears in my root directory.
My first thought was that maybe I didn't allocate enough memory to the lambda instance. I gave it 512 MB, and the logs said it was using 416MB. Maybe there wasn't enough room to fit another file inside? So I have increased the memory provided to 1024 MB, but still no luck.
My next thought was that maybe the download was just taking a long time, so I also allowed the program to wait for 5 minutes after clicking the download to ensure that the download is given time to complete. Still no luck.
I have also tried setting the following options for chromedriver (full list of chromedriver options posted at bottom):
options.add_argument(f"--user-data-dir={'/tmp'}"),
options.add_argument(f"--data-path={'/tmp'}"),
options.add_argument(f"--disk-cache-dir={'/tmp'}")
and also setting tempfolder = mkdtemp() and passing that into the chrome options as above in place of /tmp. Still no luck.
Since this applicaton is in a container, it should run the same locally as it does on AWS. So I am wondering if it is part of the config outside of the container that is blocking my ability to download a file? Maybe the request is going out but the response is not being allowed back in?
Please let me know if there is anything I need to clarify -- Any help on this issue is greatly appreciated!
Full list of Chromedriver options
options.binary_location = '/opt/chrome/chrome'
options.headless = True
options.add_argument('--disable-extensions')
options.add_argument('--no-first-run')
options.add_argument('--ignore-certificate-errors')
options.add_argument('--disable-client-side-phishing-detection')
options.add_argument('--allow-running-insecure-content')
options.add_argument('--disable-web-security')
options.add_argument('--lang=' + random.choice(language_list))
options.add_argument('--user-agent=' + fake_user_agent.user_agent())
options.add_argument('--no-sandbox')
options.add_argument("--window-size=1920x1080")
options.add_argument("--single-process")
options.add_argument("--disable-dev-shm-usage")
options.add_argument("--disable-dev-tools")
options.add_argument("--no-zygote")
options.add_argument(f"--user-data-dir={'/tmp'}")
options.add_argument(f"--data-path={'/tmp'}")
options.add_argument(f"--disk-cache-dir={'/tmp'}")
options.add_argument("--remote-debugging-port=9222")
options.add_argument("start-maximized")
options.add_argument("enable-automation")
options.add_argument("--headless")
options.add_argument("--disable-browser-side-navigation")
options.add_argument("--disable-gpu")
driver = webdriver.Chrome("/opt/chromedriver", options=options)```
Just in case anybody stumbles across this queston in future, adding the following to chrome options solved my issue:
prefs = {
"profile.default_content_settings.popups": 0,
"download.default_directory": r"/tmp",
"directory_upgrade": True
}
options.add_experimental_option("prefs", prefs)

How to use the WinRM C++ API in a simple example

why is my code failing to run a simple executable using WinRM's C++ API?
//main.cpp
int main()
{
ShellClient *shellClient = new ShellClient();
//Set up the shell client here and connect to the localhost.
//This seems to be working fine because I'm handling every
//possible error code, and none of them are being triggered
PCWSTR commandLine = L"\"MyExampleExecutable.exe\"";
isOk = shellClient->RunCommand(commandLine);
if (!isOk)
return 1;
return 0;
}
//ShellClient.cpp
bool ShellClient::RunCommand(PCWSTR command)
{
WSMAN_SHELL_ASYNC createCommandAsync;
ZeroMemory(&createCommandAsync, sizeof(createCommandAsync));
createCommandAsync.operationContext = this;
createCommandAsync.completionFunction = (WSMAN_SHELL_COMPLETION_FUNCTION)CommandCreatedCallback;
WSManRunShellCommand(shellHandle, 0, command, NULL, NULL, &createCommandAsync, &commandHandle);
if (commandHandle == NULL)//It is *always* NULL
{
std::cout << "command handle null" << std::endl;
system("pause");
return false;
}
return true;
}
One possible clue is that my C++ code thinks the shell gets created fine, but in the Event Viewer for my machine, there is this:
WSMan operation CreateShell failed, error code 2150859250
At the time of writing, this lovely error code gives precisely zero results when put into Google, making it rather difficult to know what it means.
Background and common solutions which I have already checked
As documented here and explaned in this video by the same author, most WinRM issues boil down to either connection or authentication problems. In my case, if I deliberately enter incorrect user credentials, I get an authentication error, so I know that my program is connecting and authenticating fine when the correct username and password are supplied. Also:
From the command line, I can connect to my local machine and pretend it's a remote server, for example the following command works fine:
winrs -r:http://localhost:5985 -u:COMPUTERNAME\Jeremy "dir"
winrm quickconfig shows the service is working (which we already know otherwise the winrs command wouldn't work)
winrm get winrm/config shows TrustedHosts = localhost, AllowUnencrypted = true, and all authentication methods are set to true
Following this advice, I have set the registry key HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System\LocalAccountTokenFilterPolicy = 1
Working in Windows 10
Thank you in advance!
I wasn't aware of this so can't comment on whether it's common knowledge but Microsoft have a nifty error lookup tool where you can enter an error code (after converting it from a normal number to hexadecimal) and it tells you what it means.
In this case, 2150859250 (803381F2 in hex) corresponds to:
ERROR_WINRS_IDLETIMEOUT_OUTOFBOUNDS wsmerror.h
# The WS-Management service cannot process the request. The
# requested IdleTimeout is outside the allowed range.
When setting up the WinRM shell, I was doing the following:
WSMAN_SHELL_STARTUP_INFO startupInfo;
ZeroMemory(&startupInfo, sizeof(startupInfo));
startupInfo.idleTimeoutMs = 1000;//not large enough!
startupInfo.workingDirectory = L"C:\\";
//other parameters of startupInfo set here
WSManCreateShell(session, 0, shellUri, &startupInfo, NULL, NULL, &createShellAsync, &shellHandle);
Changing idleTimeoutMs from 1000 to a much larger number like 100000 solved the error and my program now works fine.
Since the official docs for this parameter say anything between 0 and 0xFFFFFFFF are valid, it remains a mystery why a value of 1000 is throwing this error. I leave this for somebody more knowledgable than myself to answer, on the off chance that they come across this question.

redhawk module service function usage example crashes

So I am building a redhawk module and trying to just pass data through it as a test. After putting their example of how to work with input and output ports into the serviceFunction() I am able to build the module with no errors (I changed variable names to match my ports). When I put the module on the white board and link it up it's fine but as soon as I start the module it crashes. I added a line to write the incoming stream id to the console and that will hit the console 10 to 20 times before the crash (it correctly writes the id of the signal generator that is providing the signal). If I plot the output port nothing is plotted before the crash (when I say crash I mean that the module just disappears from the white board, the ide is still up and running).
The service function is:
int freqModFrTest_i::serviceFunction()
{
bulkio::InFloatPort::dataTransfer *tmp = dataFloatIn->getPacket(bulkio::Const::BLOCKING);
if (not tmp) { // No data is available
return NOOP;
}
else
{
std::cout<<tmp->streamID<<std::endl;
std::vector<float> outputData;
outputData.resize(tmp->dataBuffer.size());
for (unsigned int i=0; i<tmp->dataBuffer.size(); i++) {
outputData[i] = (float)tmp->dataBuffer[i];
}
// NOTE: You must make at least one valid pushSRI call
if (tmp->sriChanged) {
ComplexOut->pushSRI(tmp->SRI);
}
ComplexOut->pushPacket(outputData, tmp->T, tmp->EOS, tmp->streamID);
delete tmp; // IMPORTANT: MUST RELEASE THE RECEIVED DATA BLOCK
return NORMAL;
}
}
Has anyone had a similar issue or any ideas on what would be causing this?
Additional Info:
Following the sugestion by pwolfram I built a sig generator and this component into a waveform. When launching it from a domain I got the error:
2016-01-14 07:41:50,430 ERROR DCE:aa1a189e-0b5b-4968-9150-5fc3d501dadc{1}:1030 -
Child process 3772 terminated with signal 11
when trying to restart the component (as it just stoped rather then disapering) I get the following error:
Error while executing callable. Caused by org.omg.CORBA.TRANSIENT:
Retries exceeded, couldn't reconnect to 10.62.7.21:56857
Retries exceeded, couldn't reconnect to 10.62.7.21:56857
In REDHAWK 2.0.0 I created a component with the same name (freqModFrTest) and port names (dataFloatIn and ComplexOut) and used your service function verbatim. I did not however get any issues.
Here are a few things to try:
Clean and rebuild the component. The Sandbox (what you referred to as the whiteboard) will run the binary that has been built. It is possible that you've modified the code and have an older version of the binary on disk. Right click on the project and select "clean project". Then right click and select "Build Project" this will make sure that the binary matches your source code.
Run the component in debug mode. If you double click on the SPD file, under the "overview" tab there is "Debug a component in the sandbox". This will launch the component in the chalkboard within a debugging context. You can set breakpoints and walk through the code line by line. If you set no breakpoints though the IDE will stop execution when a fatal error occurs. If there is an issue (like invalid memory access) the IDE will prompt you to enter debug mode and it should point out the line in code where the issue is.
If those options fail, you can enable core dumps and use GDB to see where in the code the issue is occurring. There are lots of tutorials online for GDB but the gist is that before launching the IDE, you'll want to type "ulimit -c unlimited" then from the same terminal, launch the IDE. Now when your component dies, it will produce a core file.
Hopefully one of these gets you going down the right path.

Why is a Remote WMI call to Win32_Printer Coming Back With An Empty Set For Some Machines?

I am using WMI (prototyping everything in VBScript first, as examples are more plentiful and it removes VBScript/Python impedence) to connect remotely to a fresh PC (we will call this PC2). Most Win32_* classes can be remotely read, yet Win32_Printer returns an empty set when queried, but only when I query remotely. The resulting SWbemObjectSet always has a .Count of zero. No error. I can connect to PC1 and receive a SWbemObjectSet with a non-zero .Count, can iterate through it, etc. If I run the script locally (after removing the superuser username and password from the .ConnectServer method, naturally), I get a non-zero .Count back and can iterate through it. Even if I foolishly use my own Domain Administrator account, the problem persists. The Script:
strComputer = "nnn.nnn.nnn.nnn"
username = "DOMAIN\superuser"
password = "thisisaverygoodpassword"
Set objSWbemLocator = CreateObject("WbemScripting.SWbemLocator")
objSWbemLocator.Security_.ImpersonationLevel = 3
objSWbemLocator.Security_.AuthenticationLevel = 6
Set objSWbemServices = objSWbemLocator.ConnectServer(strComputer, "root\cimv2", username, password)
Set colSWBemObjectSet = objSWbemServices.ExecQuery("Select * From Win32_Printer")
WScript.Echo colSWBemObjectSet.Count & " Found."
For Each objPrinter in colSWBemObjectSet
For Each Property in objPrinter.Properties_
If TypeName(Property.Value) = "Variant()" Then
Wscript.Echo """" & Property.Name & """, """ & TypeName(Property.Value) & """, ""Skipping ..."""
Else
Wscript.Echo """" & Property.Name & """, """ & TypeName(Property.Value) & """, """ & Property.Value & """"
End If
Next
Next
Commenting and error checking have been omitted for brevity.
It does not appear to be a firewall problem.
Reason 1: Where a firewall blockage does exist, I receive an error
back from SWbemLocator, "The RPC server is unavailable."
Reason 2: I can access and run through the WMI class Win32_ComputerSystem
with ease.
It does not appear to be a username/password problem.
Reason 1: I can retrieve information from Win32_ComputerSystem.
Reason 2: I ought to get an error.
It does not appear to be an OS version problem:
Reason: PC2 and PC1 are both running Windows 7 Professional. PC1 is running the 64-bit version, PC2 the 32-bit.
Although I started trying to reach a 32-bit machine from a 64-bit server, it does not appear to be a 32-bit vs. 64-bit problem.
Reason 1: I added a value of 32 for __ProviderArchitecture in a SWbemNamedValueSet prior to my .ConnectServer attempt (with that SWbemNamedValueSet in the arguments to no avail), although I was unable to later add that same context to the .ExecQuery method of the connected server without a type mismatch operator.
Reason 2: I later ran the script from a 32-bit server with the same result.
It does not appear to be a corrupted WMI problem.
Reason: Once I stop using credentials, I can run the script from the target machine itself and receive a result set with more than zero items and can iterate through it.
It does not appear to be a credential/namespace mistake within my script.
Reason: Using WBemTest.exe from the same source machine and using identical username, password, authentication level, impersonation level, namespace, and so forth, I receive the same null set for an answer.
It does not appear to be an issue of WMI Namespace security on the target machine.
Reason 1: Logging in to the target machine with the same credentials as the script uses generates results.
Reason 2: Win32_Printer is in the same namespace as Win32_ComputerSystem. Win32_ComputerSystem works.
Reason 3: After using the Wmimgmt.msc Microsoft Management Console (MMC) to give the superuser full permissions, starting in the root namespace, propagating to "This namespace and subnamespaces," rebooting, and checking again, I still receive the same empty set.
It does not appear to be the respective OUs of PC2 and PC1 that are the problem.
Reason: I swapped the OUs each machine was in and rebooted. No change.
It does not appear to be the Local Computer Groups:
Reason: I made the membership of groups in PC2 look like PC1 and rebooted. No change.
It does not appear to be something magical about Win32_Printer in that remote access does not work.
Reason: I can read PC1's Win32_Printer class.
It does not appear that my WQL is unusual.
Reason: "SELECT * FROM Win32_Printer" is my test case.
It does not appear that my DCOM settings are off.
Reason: They appear identical when I go through PC1 and PC2.
I have even gone so far as to hit the Trace logs in WMI-Activity, print them out for both PC1 and PC2, then sort by GroupOperationID, OperationID (the TimeCreated SystemTime is not granular enough and EventID seems ... out of order. I can see events from the following actions:
IWbemServices::Connect
Start IWbemServices::ExecQuery - Select * from __ClassProviderRegistration
Start IWbemServices::GetObject - __Win32Provider.Name="WmiPerfClass"
Start IWbemServices::ExecQuery - references of {__Win32Provider.Name="WmiPerfClass"}
Start IWbemServices::GetObject - Win32_Printer
Start IWbemServices::ExecQuery - Select * From Win32_Printer
Provider::CreateInstanceEnum - Win32_Printer
in both sets of logs, and if I sort by GroupOperationID, OperationID they appear to happen in identical order. Sorting by EventID shows a somewhat different order. That's the closest I can see to a difference. I'm stumped at this point.
I know this verges perilously close to a system administration issue.
Found this link in the win32_printer spec page referring to this problem http://www.lansweeper.com/forum/yaf_postsm18178_WMI-Security-PowershellLansweeper.aspx#post18178 It appears only printers installes for this user are returned, not all printers on the system. So if you've never logged on to the remote system under the credentials of the user you are using to enumerate the printers then you get an empty result.
Looks like you've had a good shot at it. ServerFault might yield something more...
It's a long shot, but I once heard terminal services being disabled aparently caused issues when issuing WMI queries...
Edit:
This may not apply, but could be worth a look: AD Delegation

First call to Windows Performance Counters (PDH) sometimes fails

I'm having a problem where sometimes my code will function correctly, but other times it will fail.
This is the first bit of PDH related code that I run:
const std::wstring pidWildcardPath = L"\\Process(*)\\ID Process";
DWORD bufferSize = 0;
LPTSTR paths = NULL;
PDH_STATUS status = PdhExpandCounterPath(
pidWildcardPath.c_str(),
paths,
&bufferSize);
checkPDHStatus(status, PDH_MORE_DATA, L"Expected request for more data.");
The result of the PdhExpandCounterPath function call is 0x800007D0 (PDH_CSTATUS_NO_MACHINE). The checkPDHStatus function is a simple function that I wrote that asserts that the status is equal to the second parameter. In this case, I expect the result to be PDH_MORE_DATA because paths is NULL and bufferSize is 0. The goal of this call is to determine the size of the buffer I must allocate to store all of the results for a subsequent call to PdhExpandCounterPath. This is described in the PDH documentation under the Remarks section.
The list of PDH error codes describes PDH_MORE_DATA as "Unable to connect to the specified computer, or the computer is offline." As you can see by the performance counter path in the code above, I am not even trying to connect to a different computer than my own.
It is interesting the way that this code fails. Sometimes it works fine and then other times, it will fail on multiple back-to-back executions of my application. I have #include <pdh.h> in my header file and I have a section in my property sheet for this DLL that looks like this:
<Tool
Name="VCLinkerTool"
AdditionalDependencies="pdh.lib"
/>
I'm not sure if it matters, but this program is built by Visual Studio 2005 and run on Windows XP. Am I doing something incorrectly?
I'm a co-worker of Dave's and have discovered the following during my investigation:
the code above runs fine when run from a logged-in interactive session
the code runs fine when initiated as a Scheduled Task AND the user is logged in at the time the scheduled task is fired off
the code FAILS only when run as a Scheduled Task AND the user is NOT logged in at the time the task starts
the code continues to fail if the user logs in after the failing task has started but while it is still running (because it is looping "endlessly" until it gets a PDH_MORE_DATA status back).
In the failing instances, the following environment variables have not been established/set for the program: APPDATA, HOMEDRIVE and HOMEPATH ... I don't think this is a problem. However, the failing program also lacks the SeCreateGlobalPrivilege from its token; the passing programs all have this privilege in the token and PERFMON shows it as "Default Enabled". The other difference is that failing program has the NT_AUTH\BATCH user group in the token, while the passing program has NT_AUTH\INTERACTIVE instead ... all other user groups and privileges are the same for both cases. I think the global privilege is coming from the interactive login, but don't know if it has any bearing on PDH operation.
I cannot find anything in the Performance Counter/PDH documentation that talks about needing any special permissions or privileges for this functionality to succeed. Is the global privilege required to use Performance Counters ?
Or is there some other context/environment difference between running Scheduled Tasks (as a specific user) when that user is/isn't logged in at the time the task starts, that would account for the PDH call succeeding/failing respectively ?
Try this format, indicating the local computer:
const std::wstring pidWildcardPath = L"\\.\Process(*)\ID Process";