can we validate value of guestInfo properties set in ovf file - vsphere

I have set guestInfo properties in ovf file in ProductSection and i am able to read those properties inside VM, but i want to validate those properties when user tries to set values from UI during deployment of ova/ovf
eg.
<Property ovf:key="guestinfo.ipv4.ipaddr" ovf:type="string" ovf:userConfigurable="true"ovf:value="10.243.16.53">
<Label>IPv4 IPAddress</Label>
<Description>IP address for IPv4.(required only when IPv4 protocol is static, else can keep it blank)</Description>
</Property>
i want to validate user input(ip address) to see if its valid ipv4 or not and indicate user about it

As far as I am aware, the only way you can detect if someone has added extraConfig is through the vCenter events. How you go about indicating that to the user is up to you.
A potential solution might be to use GOVC to detect an extraConfig event, or another vSphere CLI/SDK:
govc events -f | grep 'extraConfig'
The above command will return something like this when someone alters the extraConfig:
config.extraConfig("guestinfo.test"): (key = "guestinfo.test", value = "I am some extraConfig");
You could then parse this and if it is invalid ipv4, trigger an alarm on the object, or whatever you deem to be appropriate.
A more rigorous solution would be to produce a vSphere local plugin to allow your users to add extraConfig in a manner that you can control and validate.
Hope this helps!

Related

What is the meaning of 'sender=:1.478' in dbus-monitor?

Nowadays I am analyzing d-bus in Chromium OS (Chrome OS).
I captured meaningful d-bus method calls (below), when I press ''guest' button on login UI.
my-cros # dbus-monitor --system "path=/org/chromium/Session Manager"
method call time=1632311881.319994 sender=: 1.478 -> destination=org.chromium. SessionManager serial=378 path=/org/chromium/Session Manager; interface=org.chromium.SessionManager Interface: member=LoadShil1Profile
string "$guest"
method call time=1632311881.319417 sender:1.478 -> destination=org. chromium. Session Manager serial=371 path=/org/chromium/SessionManager; interface=org.chromium.SessionManager Interface: member-SetFeatureFlagsFor User string "$guest"
array [
]
array [
]
I know that org.chromium.SessionManager is the one who starts guest/google-id session.
Btw what is the meaning of 'sender=:1.478'?
And how to track the sender process?
Thank you in advance.
Firstly, you might find it easier to visualise what’s going on by using Bustle instead of dbus-monitor.
sender=:1.478 means the message you’re looking at was sent by the connection with unique ID :1.478 on the bus. Each connection to the bus (roughly, each process, although a process can actually have more than one connection) has a unique ID, and some connections also have ‘well-known’ IDs which look like reverse-DNS names. For example org.chromium.SessionManager.
You can track the sender process by looking for the same unique ID appearing as the sender or destination of other messages. Using Bustle will make this easier, as it can group and filter messages by sender/destination.

send_v3trap context value

I am developing shared library and subagent for net-snmp. I need to send v3 traps for specific hardware events. I would like to know what value need to be filled in the context value of send_v3trap API.
void send_v3trap(netsnmp_variable_list * vars,const char * context )
Is this context value, same as user defined engine id ? i.e., the one which needs to be configured in snmptrapd.conf as below ?
createUser -e ENGINEID myuser SHA "my authentication pass" AES "my encryption pass"
More on configuring in this link
There is an example source code available for sending
v2traps
By looking at the net-snmp source code, send_v3trap calls internally send_v2trap and eventually,
/* A context name was provided, so copy it and its length to the v2 pdu
* template. */
if (context != NULL)
{
template_v2pdu->contextName = strdup(context);
template_v2pdu->contextNameLen = strlen(context);
}
Answering my own question.
"context" value can be filled with
value returned by "snmpv3_get_engineID"
NULL
As long as, configurations are proper in terms of v3 i.e., trapsess -v3 specified in the host and on the target, engineid of net-snmp is specified, then everything works fine.
Only unclear part still is, if someone is able to send v3 traps without specifying "context", in which scenario would it be useful really !

Which control codes have be implemented in the control handler of a service

The SERVICE_STATUS documentation says this structure has to filled out when calling the SetServiceStatus() function.
The third field is dwControlsAccepted.
Unfortunately I have not found any information about which control codes MUST ALWAYS be implemented/react to, at least.
The page says:
By default, all services accept the SERVICE_CONTROL_INTERROGATE value.
But, is there a problem when the service control handler does not react to the SERVICE_CONTROL_STOP control code? Is there a problem when the service control handler does not at least call SetServiceStatus() in this case?
As far as dwControlsAccepted is concerned, there are no mandatory control codes. You can set this value to zero if that meets your needs. Apart from SERVICE_CONTROL_INTERROGATE your code does not need to handle any control codes that you have not specified as acceptable.
For example, if you have not set SERVICE_ACCEPT_STOP then Windows will never send you the SERVICE_CONTROL_STOP control. Any attempt to stop the service will result in error 1052, "The requested control is not valid for this service."
Note that unless you have a specific need to perform a clean shutdown (for example, because you have a database file that has to be properly closed) you do not need to accept shutdown controls either. Such a service will continue to run until the computer is actually powered down.
If you always set dwControlsAccepted to zero, this is all you need for a control handler:
static DWORD WINAPI ServiceHandlerEx(DWORD control, DWORD eventtype, LPVOID lpEventData, LPVOID lpContext)
{
if (control == SERVICE_CONTROL_INTERROGATE)
{
return NO_ERROR;
}
else
{
return ERROR_CALL_NOT_IMPLEMENTED;
}
}

MS CryptoAPI - Machine Keystore with Error 0x80090016 (NTE_BAD_KEYSET) with certreq created keys

Summary
I create a PKCS#10 CSR with certreq and have set the option Exportable=TRUE. This successfully creates a key under the location REQUEST. I also have a valid certificate with key in MY. If I try to access any one of them the CryptoAPI reports error code 0x80090016.
Running under different access rights could not solve this problem so far.
Goal
My goal is to get both the keys in MY and REQUEST. If I call CryptAcquireContextA() on any of those, it fails.
System
Windows 7 x64
Sample Source Code
My complete code looks like this:
hStore = CertOpenStore(CERT_STORE_PROV_SYSTEM_A, 0, 0, CERT_SYSTEM_STORE_LOCAL_MACHINE, "REQUEST");
pCert = CertFindCertificateInStore(hStore, X509_ASN_ENCODING, 0, CERT_FIND_SUBJECT_STR_A, "CERTIFICATE_SUBJECT", NULL);
CertGetCertificateContextProperty(pCert, CERT_KEY_PROV_INFO_PROP_ID, NULL, &len);
pinfo = (CRYPT_KEY_PROV_INFO *) malloc(len);
CertGetCertificateContextProperty(pCert, CERT_KEY_PROV_INFO_PROP_ID, pinfo, &len);
provname = wide_to_asc(pinfo->pwszProvName);
contname = wide_to_asc(pinfo->pwszContainerName);
if(!CryptAcquireContextA(&hCryptProv, contname, provname, pinfo->dwProvType, 0)) {
err = GetLastError();
fprintf(stderr, "Error: 0x%x\n", err);
}
CryptGetUserKey(hCryptProv, pinfo->dwKeySpec, &hUserkey);
This code is mostly copied from the OpenSSL capi engine. Since the engine failed, I created the smallest possible code to search the error.
The error
If I run this, it fails with the output Error: 0x80090016. This means one of three things according to Microsoft:
Key container does not exist.
You do not have access to the key container.
The Protected Storage Service is not running.
What have I done so far?
Started service "Protected Storage"
Verified container exists with MMC & Certificate Snap-In for Local Computer
Ran the same code on the User store in user context - it worked
File System Permissions
After some googling, I tried to change permissions on the file system. I found the files by looking at the contname variable of my code and searching for the file. I changed permissions on them (more accurate, I changed permissions on the parent folder). While this fixed the issue for MY, it seems I cannot change it for REQUEST.
One note here is that my container for MY seems to be here:
%APPDATA%\Microsoft\Crypto\RSA\S-1-5-21-1650336054-1974872081-316617838-545102
For REQUEST I found it under a different address:
%ALLUSERSPROFILE%\Microsoft\Crypto\RSA\MachineKeys
I am not sure on the workings here so I cannot explain why it would put them in different locations (one being user centric, the other one a system folder). The MY store was created with a regular administrator prompt and the command certreq -new inf_file.inf cert-csr.csr and after I received my certificate, I issued certreq -accept cert.pem. Then I created a new csr with the same command.
Different privilege levels
I tried to execute my program with the following privileges:
my local user account
admin prompt (cmd->start as administrator)
nt authority\system (whoami output)
To recieve a service prompt, I executed psexec.exe –ids cmd.exe according to a tip from MaaSters Center
Final words
Any help or guidance on how to further narrow this problem down will be greatly appreciated.
I was finally able to solve this problem and it is a lot simpler than I thought. I was sure that I would receive an unambiguous container name and don't need to be more specific but CryptAcquireContext actually requires me to pass a flag CRYPT_MACHINE_KEYSET.
So my function call has to look like this:
CryptAcquireContextA(&hCryptProv, contname, provname, pinfo->dwProvType, CRYPT_MACHINE_KEYSET)
Unfortunately this is not supported by the OpenSSL engine, so you would have to alter it yourself in the engine.
See MSDN: "A key container created without this flag by a user that is not an administrator can be accessed only by the user creating the key container and the local system account."
Complete details here: https://msdn.microsoft.com/en-us/library/windows/desktop/aa379886(v=vs.85).aspx

Get the logged in Windows user name associated with a desktop

I wish to enumerate all desktops in a system and get the logged in user name for that desktop. So far I have the following code snippit as an example of obtaining a HDESK handle and trying to determine the user name associated with it (if any), but the call to LookupAccountSid fails with ERROR_NONE_MAPPED ("No mapping between account names and security IDs was done").
HDESK desk = OpenDesktop( "Default", 0, FALSE, READ_CONTROL | DESKTOP_READOBJECTS );
DWORD size = 4096;
SID * sid = (SID *)malloc( size );
GetUserObjectInformation( desk , UOI_USER_SID, sid, size, &size );
char name[512], domain[512];
int namesz = 512, domainsz = 512;
LookupAccountSid( NULL, sid, &name, &namesz, &domain, &domainsz, &s);
It might be because I am pulling out a logon SID via GetUserObjectInformation rather then a user SID. If so can I convert that to the logged in users SID?
Can anybody point me in the right direction for getting the logged in user name for an arbitrary desktop (via either it's respective HDESK or HNWD handle or even the desktop's stations HWINSTA handle)? thanks in advance.
If what you want is the user information then this will work.
call WTSEnumerateSessions to obtain an array of WTS_SESSION_INFO structures. for each structure, pass the SessionId member to WTSQuerySessionInformation with the WTSInfoClass member set to WTSUserName. This will give you the name of the user (if there is one) associated with the session.
Alternatively you can set the WTSInfoClass to WTSSessionInfo and get a WTSINFO structure back. This contains a lot of information including the user name and domain. Look at the header file definition of WTSINFO though as the MSDN page is wrong.
You have to call WTSEnumerateSessions twice, once to get the required buffer size and then once to get your information.
Relationships: One or more Desktop objects are in a Windows Station. A Windows Station is associated with a Session.
The problem is that desktops aren't associated with users at all. Try using psexec to run Notepad under the SYSTEM account. It's running on your window station, on your desktop. Otherwise, you wouldn't be able to see it.
But if you want to get the session associated with the window station, then yes it's possible. You need to call NtQueryObject with ObjectNameInformation to get the name of the object. For example, here's what I get: \Sessions\1\Windows\WindowStations\WinSta0. There's your session ID.
This is not a solution but is a good description of station/desktop. From http://www.microsoft.com/technet/security/bulletin/fq00-020.mspx
What's a windows station?
A windows station is a secure container that contains a clipboard, some global information, and a set of one or more desktops. A Windows 2000 session will have several windows stations, one assigned to the logon session of the interactive user, and others assigned to the Winlogon process, the secure screen saver process, and any service that runs in a security context other than that of the interactive user.
The interactive window station assigned to the logon session of the interactive user also contains the keyboard, mouse, and display device. The interactive window station is visible to the user and can receive input from the user. All other window stations are noninteractive, which means that they cannot be made visible to the user, and cannot receive user input.
What's a desktop?
A desktop is a secure container object that is contained within a window station. There may be many desktops contained within a windows station.
A desktop has a logical display surface and contains windows, menus, and hooks. Only the desktops of the interactive window station can be visible and receive user input. On the interactive window station, only one desktop at a time is active. This active desktop, also known as the input desktop, is the one that is currently visible to the user and that receives user input.
You could extract it from the end of the %USERPROFILE% environment variable
nbtstat used to be able to do this from the command line, with either a machine name or IP address. It's been a long time since I looked at it, though.
Correct code that worked for me:
TCHAR username[UNLEN + 1];
DWORD size = UNLEN + 1;
GetUserName((TCHAR*)username, &size);
I'm using Visual Studio Express 2012 on Windows 7 x86

Resources