|
Works fine under Windows 2000. The possibility that a message would be removed ( thus breaking software for newer OS's ) seems odd to me. I reckon you're probably pretty safe to use it.
Christian
As I learn the innermost secrets of the around me, they reward me in many ways to keep quiet.
Men with pierced ears are better prepared for marriage. They've experienced pain and bought Jewellery.
|
|
|
|
|
I am trying to find the current directory of my application on a HPC2000 operating system using Visual C++ 3.0 Embedded. The function GetCurrentDirectory does not seem to exist for the embedded environment. Anybody solve this problem, or have any hints to get me started.
Don
|
|
|
|
|
Not sure if this is what you're after, but it will get you the dir that your exe is in. Ive tested this on a PocketPC device. I dont have any HPC's available atm.
TCHAR szModule[512];
DWORD dwResult = ::GetModuleFileName(AfxGetApp()->m_hInstance, szModule, 512);
if(dwResult == 0) return;
CString strInstallDir = szModule;
int pos = strInstallDir.ReverseFind('\\');
strInstallDir = strInstallDir.Left(pos+1);
|
|
|
|
|
Ooops... the last part was from a non-unicode project.
int pos = strInstallDir.ReverseFind(L'\\');
will fix it.
|
|
|
|
|
As we know, when we click left button of mouse on the menu item of menu bar, it will mapping it with it's handling function. But how could i how could do the same thing with click right button of mouse??
Help~~~
|
|
|
|
|
Why would you want to confuse your users in this way ?
Christian
As I learn the innermost secrets of the around me, they reward me in many ways to keep quiet.
Men with pierced ears are better prepared for marriage. They've experienced pain and bought Jewellery.
|
|
|
|
|
I don't think it's possible since WM_COMMAND is fired only for regular left-button clicks. Christian is right though, why do something so weird?
Regards,
Alvaro
|
|
|
|
|
How can I launch a new child frame from a inherited CView class??
|
|
|
|
|
Do you mean a new instance of a CView derived class in an MDI app, or do you mean a new child window that is the child of a CView derived class ?
Christian
As I learn the innermost secrets of the around me, they reward me in many ways to keep quiet.
Men with pierced ears are better prepared for marriage. They've experienced pain and bought Jewellery.
|
|
|
|
|
The idea is this:
Now that I've got the communication between my CMouse and CHtlm2View classes, I want that based in some information that my CMouse class give to my View class, launch a new chils windows with another html page displayed on it. I dont' know if this can be done from the View? Or shoul I launch it from the CMainframe class?? Anyway I don't how to do it....
|
|
|
|
|
Your document template ( which is in CMainframe ) has the method CreateNewFrame, which takes a pointer to the document associated with the view and returns a CFrameWnd*. Then you need to call InitialFrameUpdate on the template also, passing in the frame pointer and doc pointer. The best place for this is your document, because you can use theApp global variable to access the template, and 'this' for the document.
Christian
As I learn the innermost secrets of the around me, they reward me in many ways to keep quiet.
Men with pierced ears are better prepared for marriage. They've experienced pain and bought Jewellery.
|
|
|
|
|
Can't use theApp variable. Doesn't recognize it!!
|
|
|
|
|
try putting an extern statement in, if it's an MFC app wizard generated app, then it is there. You can get the app as easily with AfxGetApp() if you need it.
Christian
After all, there's nothing wrong with an elite as long as I'm allowed to be part of it!! - Mike Burston Oct 23, 2001
|
|
|
|
|
Yep it worked! sorry I should do a little research eh?? Anyway tnx
|
|
|
|
|
Hi,
I know how to use the PSI.DLL (was it?) for checking a process' memory usage etc. But how can I get information about each process' CPU usage? I want to include a CPU usage bar in my software to display how much CPU that software is using.
Hints anyone?
|
|
|
|
|
WMI provides that information. I don't remember the specific profider. something like WIN32_Process. There are some examples of exactly what you are trying to do. I saw them while looking for some other WMI code. Just do some searches on google, code guru etc. You'll find them.
Hope this helps,
Bill
|
|
|
|
|
I managed to find PDH.DLL which uses either WMI or Registry data. I can get CPU usage from here, MSDN also contains docs on this DLL. Only problem now is I can't understand how to get process CPU usage, which functions, do I use Counters etc, how do I set them up?
An example would be perfect.
|
|
|
|
|
I don't know which method your asking about...
With WMI, get all instances of Win_32_Processor provider and query the LoadPercentage. This will return an average over 1 second.
Here is the class I ended up using in my project utilizing the PDH.dll. I create an instance of the class for each cpu on the system, query each and take an average, when I want to know the answer.
Class definition:
#ifndef __CPUUSAGE_CLASS__
#define __CPUUSAGE_CLASS__
#include<pdh.h>
class CCPUUsage {
public:
CCPUUsage();
~CCPUUsage();
#pragma message("CCPUUsage")
BOOL Init(LONG nMinTicksBetweenSamples = 1000, int iProcessor = 0);
int GetUsage(PBOOL pfNewSample = NULL);
private:
HQUERY m_hQuery;
HCOUNTER m_hCounter;
int m_nMinTicksBetweenSamples;
DWORD m_msLastTick;
int m_nLastSampledCPUUsage;
};
#endif // __CPUUSAGE_CLASS__
Class implementation:
CCPUUsage::CCPUUsage()
{
}
CCPUUsage::~CCPUUsage()
{
PdhCloseQuery(m_hQuery);
}
BOOL CCPUUsage::Init(LONG nMinTicksBetweenSamples, int iProcessor)
{
m_nMinTicksBetweenSamples = nMinTicksBetweenSamples;
m_msLastTick = 0;
// m_msLastTick = GetTickCount();
PDH_STATUS pdhs = PdhOpenQuery(NULL, 0, &m_hQuery);
CString csPath;
csPath.Format("\\Processor(%d)\\%% processor time", iProcessor);
pdhs = PdhAddCounter(m_hQuery,
TEXT(csPath), 0, &m_hCounter);
CString strDiag;
strDiag.Format("CCPUUsage::Init, pdhs = %x, Processor = %d",pdhs,iProcessor);
TRACEX(strDiag);
m_nLastSampledCPUUsage = 0;
return (pdhs == 0);
}
int CCPUUsage::GetUsage(PBOOL pfNewSample ) {
BOOL fNewSample;
if (pfNewSample == NULL)
pfNewSample = &fNewSample;
*pfNewSample = FALSE;
DWORD msCurrentTick = GetTickCount();
DWORD msLastTick = m_msLastTick;
if (msCurrentTick < msLastTick) {
// Wrap around, always sample
*pfNewSample = TRUE;
} else {
if ((msLastTick + m_nMinTicksBetweenSamples) < msCurrentTick) {
// It's been long since the last sample, get a new sample
*pfNewSample = TRUE;
}
}
CString szdiag;
if (*pfNewSample) {
if ((DWORD) InterlockedExchange((PLONG) &m_msLastTick, msCurrentTick) == msLastTick) {
PdhCollectQueryData(m_hQuery);
PDH_FMT_COUNTERVALUE pdhfcv;
PDH_STATUS stat = PdhGetFormattedCounterValue(m_hCounter, PDH_FMT_LONG, NULL, &pdhfcv);
szdiag.Format("GetStatus::PdhGetFormattedCounterValue returned %x, CStatus = %x",
stat,pdhfcv.CStatus);
TRACEX(szdiag);
if (pdhfcv.CStatus != 0) return -1; // This indicate erro (CPU doesn't exist for example)
m_nLastSampledCPUUsage = pdhfcv.longValue;
} else {
*pfNewSample = FALSE;
}
}
return(m_nLastSampledCPUUsage);
}
I create an object then call its Init method. For some reason, I don't understand, the PdhOpenQuery call returns success even if the CPU doesn't exist!! So I make an additional call to GetUsage, which returns -1 if there the requested processor doesn't exist.
Usage:
CArray<CCPUUsage*, CCPUUsage *> cpus;
int nCPUCount = 0;
while (TRUE)
cpus[nCPUCount] = new CCPUUSAge();
cpus[nCPUCount].Init(50,nCPUCount);
if (cpus[nCPUCount].GetUsage == -1) break;
nCPUCount++
}
Hope this helps
Bill
|
|
|
|
|
Well, thanks, it helps to get started on CPU Usage, but it's not what I want.
What I want is to measure the CPU Usage for my specific process. I want to know how much CPU my own software is taking, the software that this code is going to go into. I want to know if my software starts to grab 90+ % of the CPU, if it does it's an error situation and action needs to be taken.
Task Manager can obviously do it, but I am unable to find out how to do. I'm reading the PDH docs on MSDN, but it's a bit over my head and I thought someone had done it, or maybe the Task Manager code is available somewhere?
|
|
|
|
|
Here's the WMI code I used for Overall CPU usage. I believe, that by changing the query to use a different provider, you can get the info you want. I've seen an example that enumerates processes and gets info about them. In any case this class is hard won knowledge and may help.
#ifndef __SYSINFO_H_
#define __SYSINFO_H_
#include "resource.h"
#include <atlctl.h>
#include <wbemidl.h>
class ATL_NO_VTABLE CSysInfo :
public CComObjectRootEx<CComSingleThreadModel>,
public IDispatchImpl<ISysInfo, &IID_ISysInfo, &LIBID_SYSLOADLib>,
public CComControl<CSysInfo>,
public IPersistStreamInitImpl<CSysInfo>,
public IOleControlImpl<CSysInfo>,
public IOleObjectImpl<CSysInfo>,
public IOleInPlaceActiveObjectImpl<CSysInfo>,
public IViewObjectExImpl<CSysInfo>,
public IOleInPlaceObjectWindowlessImpl<CSysInfo>,
public ISupportErrorInfo,
public CComCoClass<CSysInfo, &CLSID_SysInfo>
{
public:
CSysInfo()
{
m_pUnkMarshaler = NULL;
}
~CSysInfo();
DECLARE_GET_CONTROLLING_UNKNOWN()
DECLARE_REGISTRY_RESOURCEID(IDR_SYSINFO)
DECLARE_PROTECT_FINAL_CONSTRUCT()
BEGIN_COM_MAP(CSysInfo)
COM_INTERFACE_ENTRY(ISysInfo)
COM_INTERFACE_ENTRY(IDispatch)
COM_INTERFACE_ENTRY(IViewObjectEx)
COM_INTERFACE_ENTRY(IViewObject2)
COM_INTERFACE_ENTRY(IViewObject)
COM_INTERFACE_ENTRY(IOleInPlaceObjectWindowless)
COM_INTERFACE_ENTRY(IOleInPlaceObject)
COM_INTERFACE_ENTRY2(IOleWindow, IOleInPlaceObjectWindowless)
COM_INTERFACE_ENTRY(IOleInPlaceActiveObject)
COM_INTERFACE_ENTRY(IOleControl)
COM_INTERFACE_ENTRY(IOleObject)
COM_INTERFACE_ENTRY(IPersistStreamInit)
COM_INTERFACE_ENTRY2(IPersist, IPersistStreamInit)
COM_INTERFACE_ENTRY(ISupportErrorInfo)
COM_INTERFACE_ENTRY_AGGREGATE(IID_IMarshal, m_pUnkMarshaler.p)
END_COM_MAP()
BEGIN_PROP_MAP(CSysInfo)
PROP_DATA_ENTRY("_cx", m_sizeExtent.cx, VT_UI4)
PROP_DATA_ENTRY("_cy", m_sizeExtent.cy, VT_UI4)
END_PROP_MAP()
BEGIN_MSG_MAP(CSysInfo)
CHAIN_MSG_MAP(CComControl<CSysInfo>)
DEFAULT_REFLECTION_HANDLER()
END_MSG_MAP()
HRESULT FinalConstruct();
void FinalRelease()
{
m_pUnkMarshaler.Release();
}
CComPtr<IUnknown> m_pUnkMarshaler;
STDMETHOD(InterfaceSupportsErrorInfo)(REFIID riid)
{
static const IID* arr[] =
{
&IID_ISysInfo,
};
for (int i=0; i<sizeof(arr)/sizeof(arr[0]); i++)
{
if (InlineIsEqualGUID(*arr[i], riid))
return S_OK;
}
return S_FALSE;
}
DECLARE_VIEW_STATUS(VIEWSTATUS_SOLIDBKGND | VIEWSTATUS_OPAQUE)
public:
STDMETHOD(get_LoacPct)( short *pVal);
STDMETHOD(Load)();
int LoadPercentage();
HRESULT OnDraw(ATL_DRAWINFO& di)
{
RECT& rc = *(RECT*)di.prcBounds;
Rectangle(di.hdcDraw, rc.left, rc.top, rc.right, rc.bottom);
SetTextAlign(di.hdcDraw, TA_CENTER|TA_BASELINE);
LPCTSTR pszText = _T("ATL 3.0 : SysInfo");
TextOut(di.hdcDraw,
(rc.left + rc.right) / 2,
(rc.top + rc.bottom) / 2,
pszText,
lstrlen(pszText));
return S_OK;
}
IWbemLocator *pLoc ;
IWbemServices *pSvc ;
IEnumWbemClassObject *pEnum;
IWbemClassObject *pObj;
};
#endif //__SYSINFO_H_
#include "stdafx.h"
#include <comdef.h>
#include "SysLoad.h"
#include "SysInfo.h"
CSysInfo::~CSysInfo() {
pObj->Release();
pSvc->Release();
pLoc->Release();
CoUninitialize();
}
int CSysInfo::LoadPercentage()
{
return 0;
}
STDMETHODIMP CSysInfo::Load()
{
return S_OK;
}
HRESULT CSysInfo::FinalConstruct()
{
try
{
HRESULT hres = CoInitializeEx(0, COINIT_MULTITHREADED);
if(FAILED(hres))
{
throw 101;
}
hres = CoCreateInstance(CLSID_WbemLocator, 0,
CLSCTX_INPROC_SERVER,
IID_IWbemLocator,
(LPVOID *) &pLoc);
if(FAILED(hres))
{
throw 102;
CoUninitialize();
exit(1);
}
hres = pLoc->ConnectServer( _bstr_t(L"\\\\.\\root\\cimv2"),
NULL, NULL, 0, NULL, 0, 0,
&pSvc);
if(FAILED(hres))
{
throw 103;
pLoc->Release();
CoUninitialize();
exit(1);
}
hres = CoSetProxyBlanket( pSvc,
RPC_C_AUTHN_WINNT,
RPC_C_AUTHZ_NONE,
NULL,
RPC_C_AUTHN_LEVEL_CALL,
RPC_C_IMP_LEVEL_IMPERSONATE,
NULL,
EOAC_NONE);
if(FAILED(hres))
{
throw 104;
pSvc->Release();
pLoc->Release();
CoUninitialize();
exit(1);
}
BSTR language = SysAllocString(L"WQL");
BSTR query = SysAllocString(L"select * from Win32_Processor");
hres = pSvc->ExecQuery( language,
query,
WBEM_FLAG_FORWARD_ONLY,
NULL,
&pEnum);
SysFreeString(query);
SysFreeString(language);
if(FAILED(hres))
{
throw 105;
}
else
{
ULONG uReturned = 0;
hres = pEnum->Next( 0,
1,
&pObj,
&uReturned);
if(uReturned != 0) throw 106;
}
}
catch (int iErr)
{
}
return CoCreateFreeThreadedMarshaler(
GetControllingUnknown(), &m_pUnkMarshaler.p);
}
STDMETHODIMP CSysInfo::get_LoacPct(short *pVal)
{
BSTR strClassProp = SysAllocString(L"LoadPercentage");
VARIANT v;
HRESULT hres = pObj->Get(strClassProp, 0, &v, 0, 0);
SysFreeString(strClassProp);
if(!FAILED(hres))
{
*pVal = V_INT(&v);
}
VariantClear(&v);
return S_OK;
}
Hope this helps, My last shot
Bill
|
|
|
|
|
Oops, thanks a lot! I will digest this in upcoming days
|
|
|
|
|
Ok, some guesswork and trial and error...
First, as with another article I found on the net, the processor time parameter is Windows language dependant:
csPath.Format("\\Processor(%d)\\%% processor time", iProcessor);
changes into:
csPath.Format("\\Processor(%d)\\%% processortid", iProcessor);
...to work on my Swedish Windows. I don't know how to find this for any language yet.
To find the CPU Usage for a specific process use:
csPath.Format("\\Process(%s)\\%% processortid", sProcess);
for example:
csPath.Format("\\Process(iexplore)\\%% processortid");
for Internet Explorer CPU usage.
This does what I want now, except for that language dependency which I must solve now... (anyone know?)
|
|
|
|
|
Does anyone know what I need to do to create a CBitmap/HBITMAP out of an unsigned char array? I'm pretty sure it's a formatting issue but I just can't seem to do it. I'm a novice OpenGL developer and I know how to read and process bitmap files, but what am I doing wrong to create a CBitmap/HBITMAP from the data array?
Thanks,
- Mike
P.S. Of course I could always use LoadImage or whatever it is but I don't want to do it that way.
|
|
|
|
|
|
I was reading Item 7 of Scott Meyer's book, Effective C++ and decided to try the code. So I created my template header , a file that inherits from the template class and a driver (i.e. simple main) that tries to instantiate the new class.
I got the following errors on VC6 SP 5. Any ideas of what I am doing wrong? code is included below:
driver.cpp
c:\processdoc\c++\memorymanager\test.h(26) : error C2039: 'set_new_handler' : is not a member of 'std'
C:\ProcessDoc\C++\MemoryManager\driver.cpp(11) : while compiling class-template member function 'void *__cdecl NewHandlerSupport<class x="">::operator new(unsigned int)'
c:\processdoc\c++\memorymanager\test.h(35) : error C2039: 'set_new_handler' : is not a member of 'std'
C:\ProcessDoc\C++\MemoryManager\driver.cpp(11) : while compiling class-template member function 'void *__cdecl NewHandlerSupport<class x="">::operator new(unsigned int)'
c:\processdoc\c++\memorymanager\test.h(39) : error C2039: 'set_new_handler' : is not a member of 'std'
C:\ProcessDoc\C++\MemoryManager\driver.cpp(11) : while compiling class-template member function 'void *__cdecl NewHandlerSupport<class x="">::operator new(unsigned int)'
main.cpp
Error executing cl.exe.
MemoryManager.exe - 3 error(s), 0 warning(s)
And here is the code I have:
the main driver (driver.cpp):
#include "main.h"
void main(void)
{
x * yyy = new x();
}
the class (main.cpp & main.h):
#include "main.h"
x::x()
{
}
x::~x()
{
}
void x::test()
{
}
//////main.h
#include "test.h"
class x : public NewHandlerSupport<x>
{
public:
x();
~x();
void test ();
private:
};
the template (right off SM's book)..I called it test.h :
#include <new>
template<class t="">
class NewHandlerSupport {
public:
static new_handler set_new_handler(new_handler p);
static void * operator new(size_t size);
private:
static new_handler currentHandler;
};
template<class t="">
new_handler NewHandlerSupport<t>::set_new_handler(new_handler p)
{
new_handler oldHandler = currentHandler;
currentHandler = p;
return oldHandler;
}
template<class t="">
void * NewHandlerSupport<t>::operator new(size_t size)
{
new_handler globalHandler =
std::set_new_handler(currentHandler);
void *memory;
try {
memory = ::operator new(size);
}
catch (std::bad_alloc&)
{
std::set_new_handler(globalHandler);
throw;
}
std::set_new_handler(globalHandler);
return memory;
}
// this sets each CurrentHandler to 0
template <class t="">
new_handler NewHandlerSupport<t>::currentHandler;
|
|
|
|
|