|
I need to replace the WinMain implemented in MFC, by my own WinMain to encapsulate MFC initialization within the win32 service entry point function.
Does anybody got any clue?
/regards/
|
|
|
|
|
You need to tell the linker to use your WinMain version, which is done via the "Entry-point symbol" box inside Project Settings/Link/Output category.
That's the extent of my knowledge, since I've personally never done this. Take a look at "entry point" in the MSDN.
Another approach is to create a dummy Console project and add MFC support to it. There you can get the code for initializing the MFC libraries. You can then create a regular "Win32 Application" and copy that code there.
Regards,
Alvaro
All you need in this life is ignorance and confidence, and then success is sure. -- Mark Twain
|
|
|
|
|
Thank you Alvaro!
I've changed the type of linked application and included the _tmain() function and MFC initialization code from MFC library. It looks like this: <see below="">
Application starts normally, but it throws the access violation exception while destroying the application document. Wonder why.
Anyway I'll try to change the entry point from linker options.
TServiceApp Service(ServiceStart, ServiceStop); // application service object
int _tmain(int argc, const TCHAR* argv[], TCHAR* envp[])
{
int RetCode = 1;
// if(AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
{
Service.ServiceName = NETACCESS_SERVICENAME;
Service.DisplayName = NETACCESS_DISPLAYNAME;
Service.Initialize(argc, argv);
RetCode = Service.Status.ExitCode;
}
// else
// WriteServiceLog(_T("Fatal Error: MFC initialization failed.\n"));
return RetCode;
}
DWORD __fastcall ServiceStart(DWORD Count, LPTSTR *lpszArgv)
{
Service.Status.Report(SERVICE_START_PENDING); // 3000
STARTUPINFO StartupInfo;
StartupInfo.dwFlags = 0;
GetStartupInfo(&StartupInfo);
HINSTANCE hInstance = GetModuleHandle(NULL);
HINSTANCE hPrevInstance = NULL;
LPTSTR lpCmdLine = GetCommandLine();
int nCmdShow = SW_SHOWDEFAULT;
if(StartupInfo.dwFlags & STARTF_USESHOWWINDOW)
nCmdShow = StartupInfo.wShowWindow;
Service.Status.ExitCode = -1;
CWinThread* pThread = AfxGetThread();
CWinApp* pApp = AfxGetApp();
// AFX internal initialization
if (!AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow))
goto InitFailure;
// App global initializations (rare)
if(pApp != NULL && !pApp->InitApplication())
goto InitFailure;
// Perform specific initializations
if(!pThread->InitInstance())
{
if (pThread->m_pMainWnd != NULL)
{
TRACE(traceAppMsg, 0, "Warning: Destroying non-NULL m_pMainWnd\n");
pThread->m_pMainWnd->DestroyWindow();
}
Service.Status.ExitCode = pThread->ExitInstance();
goto InitFailure;
}
Service.Status.Report(SERVICE_RUNNING); // 0
Service.Status.ExitCode = pThread->Run();
InitFailure:
#ifdef _DEBUG
// Check for missing AfxLockTempMap calls
if (AfxGetModuleThreadState()->m_nTempMapLock != 0)
{
TRACE(traceAppMsg, 0, "Warning: Temp map lock count non-zero (%ld).\n",
AfxGetModuleThreadState()->m_nTempMapLock);
}
AfxLockTempMaps();
AfxUnlockTempMaps(-1);
#endif
AfxWinTerm();
return Service.Status.ExitCode;
}
VOID __stdcall TServiceApp::Initialize(DWORD Count, LPCTSTR *Args)
{
if(mServiceStart && mServiceStop)
{
SERVICE_TABLE_ENTRY DispatchTable[] =
{
{ mServiceName, TServiceApp::ServiceMain },
{ NULL, NULL }
};
if(Count > 1 && (*Args[1] == '-' || *Args[1] == '/'))
{
TCoreService Service;
TServiceManager Manager;
Service.Name = mServiceName;
Service.DisplayName = mDisplayName;
Service.Dependencies = mDependencies;
if(_stricmp(_T("install"), Args[1] + 1) == 0)
{
Manager.Install(&Service);
Service.__Start(Count, Args);
}
else
if(_stricmp(_T("remove"), Args[1] + 1) == 0)
Manager.Remove(&Service);
else
if(_stricmp(_T("debug"), Args[1] + 1) == 0)
{
TServiceHandle::sDebug = TRUE;
WriteServiceLog(_T("Debugging %s.\n"), mDisplayName);
SetConsoleCtrlHandler(ControlHandler, TRUE);
if(mServiceStart)
mServiceStart(Count, (LPTSTR*)Args);
}
else
goto Dispatch;
}
else
Dispatch:
if(!TCoreService::__StartCtrlDispatcher(DispatchTable))
WriteMessage(_T("Initialize: Failed to start service control dispatcher."));
}
else
WriteServiceLog(_T("Initialize: Start and stop routines must be specified.\n"));
}
/regards/
|
|
|
|
|
|
if you switch from statically-linked MFC to dynamically-linked MFC, you'll see the difference MFC makes.
just using enough MFC to use CDialog and CString will add over to 200K to my ATL objects.
-c
WWT2D?
|
|
|
|
|
|
Thomas George wrote:
my exe size went up from 680 KB to 1MB
the static libs my company sells nearly tripled in size with VC7. i talked with MS reps about this and they told me it was due to increased 'locale' support in the latest STL & C++ std libs.
-c
Be very, very careful what you put into that head, because you will never, ever get it out. --Thomas Cardinal Wolsey
|
|
|
|
|
Thomas George wrote:
Is there any tool to do an analysis of what constitutes an exe? like how much is MFC, how much is my actual code etc?
dumpbin.exe is surely a good start.
|
|
|
|
|
Generate a MAP file and then have a look at that. This list every function, class etc. and there address. So you can calc the size of functions as well if you want.
Neville Franks, Author of ED for Windows. www.getsoft.com
Make money with our new Affilate program
|
|
|
|
|
Hiya have just started to learn SQL and am having trouble with the INSERT and DELETE and EXECUTESQL statements. Can someone show me how to use these functions?? have tried but keep getting it wrong.
What I really need is a example program with some SQL statements being used.
I am using CDatabase and CRecordset for the database.
Thanks for your help.
grahamoj.
|
|
|
|
|
hi,
CDatabase m_db; //declare database object
CRecordset m_EmpTable; // declare recordset for employee table
//////////////////////////////////////////////////////////////////////////////
// Open connection to database ORACLE01 (must be defined as
// data source in ODBC)
TRY{
m_db.OpenEx( "DSN=ORACLE01;UID=scott;PWD=tiger" , CDatabase::noOdbcDialog );
}
CATCH( CDBException, dbe ){
MessageBox( dbe->m_strError );
}
END_CATCH
//////////////////////////////////////////////////////////////////////////////
// Insert new employee record into table Emp
TRY{
m_db.ExecuteSQL( "INSERT INTO EMP VALUES(10, 'John','Brown','Chicago')" );
}
CATCH( CDBException, dbe ){
MessageBox( dbe->m_strError );
}
END_CATCH
//////////////////////////////////////////////////////////////////////////////
// Retrieve records from table Emp based on query
CString id;
CString fname;
CString lname;
CString city;
m_EmpTable.Open( CRecordset::dynaset, "SELECT * FROM EMP" ); // open recordset
while( !m_EmpTable.IsEOF( ) ) // retrieve records one by one
{
m_EmpTable.GetFieldValue( (int)0, id );
m_EmpTable.GetFieldValue( 1, fname);
m_EmpTable.GetFieldValue( 2, lname );
m_EmpTable.GetFieldValue( 3, city );
// do something with data
m_EmpTable.MoveNext(); // move to the next record
}
or you can do it like this..
CAccountRecord rs(&db);
rs.Open( CRecordset::snapshot );
rs.AddNew();
rs.m_NAME = "Becky Dugan";
rs.m_ADDRESS = "Bustins, ME 01443";
rs.m_ID = 33;
rs.m_AMOUNT = 100000;
if(!rs.Update( )){
cout << "Record not added; no field values were set.";
return FALSE;
}
rs.Close();
m_EmpTable.Close(); // close recordset
// How to do an UPDATE
/////////////////////////////////////////////////////////
rs.Open( CRecordset::snapshot,
_T( "select * from scott.account where id=42" ));
rs.MoveFirst();
rs.Edit();
rs.m_NAME = "Robert Dugan";
if(!rs.Update( )){
cout << "Update failed." << endl;
return FALSE;
}
rs.Close();
Verify that the update happened by using sqlplus:
// How to do a DELETE
////////////////////////////////////////////////////////
rs.Open( CRecordset::snapshot );
rs.MoveLast();
rs.Delete();
rs.Close();
i hope this is done now..Cheers
Himanshu
|
|
|
|
|
Hey all. I'm having some trouble figuring out askey. How would I cycle through a file to find out how many of each letter there is, and how many spaces, periods, etc. I know each letter has a number value, but how do I convert it? Also, how would I make a vector that has a slot for each letter in the alphabet increase by 1 every time a letter is found that corrosponds to that slot in the vector?
Hopefully you understood my question .
Thanks in advance.
|
|
|
|
|
proprogram wrote:
Hey all. I'm having some trouble figuring out askey.
I haven't got a clue what "askey" is. My best guess it that you heard someone say it - in case it's spelled ASCII (American Standard Code for Information Interchange).
What you want to do is find the frequency of characters in a given file, and you are on the right track with the question:
how would I make a vector that has a slot for each letter in the alphabet increase by 1 every time a letter is found that corrosponds to that slot in the vector?
You first create a vector, or even an array since you know in advance that you'll only have to deal with at most 256 different values. Let's use the shortest code and use an array:
// The following line creates an array of 256
// unsigned integers, initializing all of them to zero.
unsigned int freq[256] = { 0 };
// 1.
// Here you are supposed to read through your file,
// one byte at a time, and put the read [unsigned char]
// value into a variable. Let's call it foo.
unsigned char foo = read_next_byte();
// 2.
// The following line uses the character value
// (if in a particular range also called the ASCII code)
// as an index into the array. Let's tell it we've found
// another character/byte with this value.
// Note that for a closed set like this (0-255), the
// index itself is actually also a data carrier.
// This can be worth recognising for further adventures
// into computing algorithms.
++freq[foo];
// Jump back to 1 until the file/stream is exhausted.
Now you can do whatever you like with your array.
++luck;
|
|
|
|
|
I'm trying to figure out how to use a file passed or used to start my application when started by a file association through either double-clicking a data file or launched from an attachment from an email. The command line passes the pathname of the file that opened the app, however since the data file is locked I can not access the data through normal file opserations. Somehow the dataptr or filehandle is being passed or managed somewhere. Can someone explain how I can get access to that handle so I can read the data file?
In paticular I want to have access to the data from an email attachment. This means that the email app or some OS mech has launched my associated app and has the file locked.
|
|
|
|
|
I am not sure I understand your question but anything might help you.
1st try rebooting your machine. If you were debugging, windows might not be able to kill the process.
If you are looking at how to, launch your app when your file type is double clicked then you need to write to the registry on your setup script.
here is a page about registry and associating files
http://members.tripod.com/mr_tweaks/mytweaks/reg23.htm[^]
Later, JoeSox www.joeswammi.com
Load my Sig here.....
|
|
|
|
|
Dr Soong wrote:
The command line passes the pathname of the file that opened the app, however since the data file is locked I can not access the data through normal file opserations
Surely you can open it read-only with read-sharing enabled? Else it would be, as you have recognized yourself, be an utterly useless mechanism. Since a multitude of programs apparently are able to do what you request, I must assume you have done something wrong. Play with the sharing flags and I'm sure you'll get something working.
Always request the least privilege you need to get the job done - this goes for everything, not just file sharing and the occasional write access.
|
|
|
|
|
I have a visual c++ program (using mfc) and I want to get the DNS of the computer where the program runs. The operating system is Windows 98. an you advise me how to get it?
|
|
|
|
|
you could use GetNetworkParams check the MSDN for more info.
|
|
|
|
|
I have a Windows Service application with 4-5 dialog boxes in it. I have good reasons to believe that it should have them, but the service would not start unless I remove them.
Anybody any ideas ?
<marquee>. . . Humans do it better . . .
|
|
|
|
|
If your running under the 'system' account you need to have "Allow service to interact with desktop" checked. This is in the Server Properties dialog that you must get to from the 'Services' control panel.
"No matter where you go, there your are..." - Buckaoo Banzi
<pete/>
|
|
|
|
|
Yes that is check'd but is there any restrictions on the size of the UI resources that can be put in a Service (that is causing me problems) ?
or
Is there any limit on the size of the service exe image loaded ?
Tnx palbano
<marquee>. . . Humans do it better . . .
|
|
|
|
|
Prabhakar wrote:
I have a Windows Service application with 4-5 dialog boxes in it. I have good reasons to believe that it should have them, but the service would not start unless I remove them.
Thumb rule: Services should not have windows or consoles that provide feedback to the user.
If the service must have a user interface, it must run under the LocalSystem account.
Any information from EventLog when you have those dialog boxes?
Follow live World Cup Cricket scores here[^]
|
|
|
|
|
Read this:
MSDN[^]
lpDesktop
Windows NT/2000/XP: Pointer to a null-terminated string that specifies either the name of the desktop, or the name of both the desktop and window station for this process. A backslash in the string indicates that the string includes both the desktop and window station names.
For CreateProcess and CreateProcessAsUser, if this member is NULL, the new process inherits the desktop and window station of its parent process. If this member is an empty string, the process does not inherit the desktop and window station of its parent process; instead, the system determines if a new desktop and window station need to be created. If the impersonated user already has a desktop, the system uses the existing desktop.
For CreateProcessWithLogonW, if this member is NULL or an empty string, the new process inherits the desktop and window station of its parent process. CreateProcessWithLogonW adds permission for the specified user account to the inherited window station and desktop. Otherwise, if this member specifies a desktop, it is the responsibility of the application to add permission for the specified user account to the specified window station and desktop.
Follow live World Cup Cricket scores here[^]
|
|
|
|
|
How do you include .NET references in C++ within VS .NET? I want to use the MailMessage object. In C# you just have to specify the following at the top of your file.
using System.Web.Mail
What is the C++ equivalent?
Thanks.
Ron Ward
|
|
|
|
|
Hie
I would like to know how to detect in realtime when another process write into a specific file. This time i try to use completion methode. A little bit like visual when we modify a opened source file by another application. Visual display a dialogBox with the question (Would you want to reload the file ?). But Visual use this juste with focus gain, and me i want to do it in real time.
I create a file sharing and use overlapped option
I try to read into the file and i use the getOverlappedResult function with bWait at TRUE to wait the reading.
I write with another process into this file
But my app still lock ever.
If somone know how to do it ?
thx
|
|
|
|