943,594 Members | Top Members by Rank

Ad:
  • C++ Discussion Thread
  • Unsolved
  • Views: 911
  • C++ RSS
May 20th, 2008
0

Any Ideas....

Expand Post »
I am just posting in the hopes that somenone can explain a problem I seem to be having with Turbo C++. My application basically has two forms (Form1 and Form2). Form1 is the main form and Form2 is created dynamically, as the result of a button click event, from Form1 with the following code:

C++ Syntax (Toggle Plain Text)
  1. TForm2 *Form2 = new TForm2(this);
  2. Form2–>ShowModal();

Form2 is not included in the Auto_Create forms list under Project Options. Form2 accesses a thread object, derived from the TThread class, called Thread. A new instance of the thread is created with the following code:

C++ Syntax (Toggle Plain Text)
  1. Thread *Thread1 = new Thread(true);

This is set running following a button click event with the following code:

C++ Syntax (Toggle Plain Text)
  1. Thread1->Resume();

The thread updates the contents of a TMemo object named Memo1 located on Form2. The thread code looks somthing like this:

C++ Syntax (Toggle Plain Text)
  1. void __fastcall Thread::Execute()
  2. {
  3. Synchronize(&UpdateMemo)
  4. }
  5. //---------------------------------------------------------------------------
  6. void __fastcall Thread::UpdateMemo(void);
  7. {
  8. Form2->Memo1->Lines->Add("Thread Running!");
  9. }
  10. //---------------------------------------------------------------------------

The UpdateMemo function is defined in the Thread header file as:

C++ Syntax (Toggle Plain Text)
  1. void __fastcall Thread::UpdateMemo(void);

For some reason this code generates an access violation and I can't figure out why. If I include Form2 in the Auto_Create forms list under Project Options the thread runs (without generating errors), but doesn't update Memo1!! If I compile Form2 on its own or include Form2 in the Auto_Create forms list under Project Options and display it using the code:

C++ Syntax (Toggle Plain Text)
  1. Form2–>ShowModal();

without creating it dynamically, the thread runs and updates Memo1 as it should. I am guessing therefore that the problem arises from the way that Form2 has been created. Any help would be much appreciated as I am really quite stumped!

Many thanks in advance.

Ben.
Last edited by BAEdwards; May 20th, 2008 at 6:19 am. Reason: Problem clarified
Similar Threads
Reputation Points: 10
Solved Threads: 0
Newbie Poster
BAEdwards is offline Offline
11 posts
since May 2008
May 20th, 2008
0

Re: Any Ideas....

Interesting.
Do you have global and/or static variables anywhere ?
Also can you post:
- TForm2.h
- TForm2::TForm2() implementation
Reputation Points: 254
Solved Threads: 74
Practically a Posting Shark
thekashyap is offline Offline
804 posts
since Feb 2007
May 20th, 2008
0

Re: Any Ideas....

Click to Expand / Collapse  Quote originally posted by thekashyap ...
Interesting.
Do you have global and/or static variables anywhere ?
Also can you post:
- TForm2.h
- TForm2::TForm2() implementation
Here is the code from all three Units. This is not the actual project I am working on but the following code replicates the problem:

Unit1.h (Form1):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #ifndef Unit1H
  4. #define Unit1H
  5. //---------------------------------------------------------------------------
  6. #include <Classes.hpp>
  7. #include <Controls.hpp>
  8. #include <StdCtrls.hpp>
  9. #include <Forms.hpp>
  10. //---------------------------------------------------------------------------
  11. class TForm1 : public TForm
  12. {
  13. __published: // IDE-managed Components
  14. TButton *Button1;
  15. void __fastcall Button1Click(TObject *Sender);
  16. private: // User declarations
  17. public: // User declarations
  18. __fastcall TForm1(TComponent* Owner);
  19. };
  20. //---------------------------------------------------------------------------
  21. extern PACKAGE TForm1 *Form1;
  22. //---------------------------------------------------------------------------
  23. #endif
Unit1.cpp (Form1):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #include <vcl.h>
  4. #pragma hdrstop
  5.  
  6. #include "Unit1.h"
  7. #include "Unit2.h"
  8. //---------------------------------------------------------------------------
  9. #pragma package(smart_init)
  10. #pragma resource "*.dfm"
  11. TForm1 *Form1;
  12. //---------------------------------------------------------------------------
  13. __fastcall TForm1::TForm1(TComponent* Owner)
  14. : TForm(Owner)
  15. {
  16. }
  17. //---------------------------------------------------------------------------
  18. void __fastcall TForm1::Button1Click(TObject *Sender)
  19. {
  20. TForm2 *Form2 = new TForm2(this);
  21. Form2->ShowModal();
  22. }
  23. //---------------------------------------------------------------------------

Unit2.h (Form2):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #ifndef Unit2H
  4. #define Unit2H
  5. //---------------------------------------------------------------------------
  6. #include <Classes.hpp>
  7. #include <Controls.hpp>
  8. #include <StdCtrls.hpp>
  9. #include <Forms.hpp>
  10. #include <ComCtrls.hpp>
  11. //---------------------------------------------------------------------------
  12. class TForm2 : public TForm
  13. {
  14. __published: // IDE-managed Components
  15. TButton *Button1;
  16. TMemo *Memo1;
  17. void __fastcall Button1Click(TObject *Sender);
  18. private: // User declarations
  19. public: // User declarations
  20. __fastcall TForm2(TComponent* Owner);
  21. };
  22. //---------------------------------------------------------------------------
  23. extern PACKAGE TForm2 *Form2;
  24. //---------------------------------------------------------------------------
  25. #endif
Unit2.cpp (Form2):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #include <vcl.h>
  4. #pragma hdrstop
  5.  
  6. #include "Unit2.h"
  7. #include "Unit3.h"
  8. //---------------------------------------------------------------------------
  9. #pragma package(smart_init)
  10. #pragma resource "*.dfm"
  11. TForm2 *Form2;
  12.  
  13. Thread *Thread1 = new Thread(true);
  14. //---------------------------------------------------------------------------
  15. __fastcall TForm2::TForm2(TComponent* Owner)
  16. : TForm(Owner)
  17. {
  18. }
  19. //---------------------------------------------------------------------------
  20. void __fastcall TForm2::Button1Click(TObject *Sender)
  21. {
  22. Thread1->Resume();
  23. }
  24. //---------------------------------------------------------------------------

Unit3.h (Thread):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #ifndef Unit3H
  4. #define Unit3H
  5. //---------------------------------------------------------------------------
  6. #include <Classes.hpp>
  7. //---------------------------------------------------------------------------
  8. class Thread : public TThread
  9. {
  10. private:
  11. protected:
  12. void __fastcall Execute();
  13. public:
  14. __fastcall Thread(bool CreateSuspended);
  15. void __fastcall Thread::UpdateMemo(void);
  16. };
  17. //---------------------------------------------------------------------------
  18. #endif
Unit3.cpp (Thread):
C++ Syntax (Toggle Plain Text)
  1. //---------------------------------------------------------------------------
  2.  
  3. #include <vcl.h>
  4. #pragma hdrstop
  5.  
  6. #include "Unit3.h"
  7. #include "Unit2.h"
  8. #pragma package(smart_init)
  9. //---------------------------------------------------------------------------
  10. __fastcall Thread::Thread(bool CreateSuspended)
  11. : TThread(CreateSuspended)
  12. {
  13. }
  14. //---------------------------------------------------------------------------
  15. void __fastcall Thread::Execute()
  16. {
  17. for (int i = 0; i <= 1000; i++)
  18. {
  19. Synchronize(&UpdateMemo);
  20. }
  21. }
  22. //---------------------------------------------------------------------------
  23. void __fastcall Thread::UpdateMemo(void)
  24. {
  25. Form2->Memo1->Lines->Add("Thread Running");
  26. }
  27. //---------------------------------------------------------------------------

Thanks,

Ben.
Reputation Points: 10
Solved Threads: 0
Newbie Poster
BAEdwards is offline Offline
11 posts
since May 2008
May 20th, 2008
0

Re: Any Ideas....

Couldn't figure anything from the code, given that it's not complete.
- How does Thread get Form2 obj?
- The access violation could be because one of the variables (Form2 or Memo1 or Lines) is uninitialized.
But can't figure out any of these from the code.
Just a couplea other thoughts:
- Check the owner's value when TForm2::TForm2(TComponent* Owner) gets called. Print out some instance specific info of TComponent that's passed. May it's different when "framework" creates it (instead of when you create it viz Form1 object)
- Other thing that I suspect more is, Memo, is an "// IDE-managed Components", so perhaps when IDE creates the Form2 (via your project settings) it takes care of init'ing it somehow?
Reputation Points: 254
Solved Threads: 74
Practically a Posting Shark
thekashyap is offline Offline
804 posts
since Feb 2007
May 20th, 2008
0

Re: Any Ideas....

Many thanks for your reply. I am afraid I am a reasonably new to C++ so you will have to excuse my ignorance.

I believe thread can locate the Form2 object by means of the include statement at the top of Unit3.cpp...
C++ Syntax (Toggle Plain Text)
  1. #include "Unit2.h"
As to the initialisation state of Form2 and Memo I am not sure how I would go about checking this. Any direction would be much appreciated. I assumed that as objects are created on the form at design time, they would initialised in exactly the same way irrespective of whether the form they are associated with is dynamically created or automatically created when the program runs. Is this not the case?

How would I go about checking the initialisation state of Form2 and Memo1 etc so I can determine whether any difference arises as the result of the different ways of creating the form? Any further help would be much appreciated.

Many thanks,

Ben.

BTW: Although the code posted is not from the project I am working on, it is complete and should compile and replicate the problem I am experiencing.
Reputation Points: 10
Solved Threads: 0
Newbie Poster
BAEdwards is offline Offline
11 posts
since May 2008
May 21st, 2008
0

Re: Any Ideas....

I think I've cracked it!! If I create Form2 using the following code

C++ Syntax (Toggle Plain Text)
  1. Form2 = new TForm2(this);
  2. Form2->ShowModal();

Instead of

C++ Syntax (Toggle Plain Text)
  1. TForm2 *Form2 = new TForm2(this);
  2. Form2->ShowModal();

the thread is now able to access the TMemo component on Form2. I'm not entirely sure why this works so if anyone has a couple of minutes spare and can offer me an explaination it would be much appreciated.

Thanks for taking the time to look at my code and offering some thoughts thekashyap . Cheers,

Ben.
Reputation Points: 10
Solved Threads: 0
Newbie Poster
BAEdwards is offline Offline
11 posts
since May 2008
May 21st, 2008
0

Re: Any Ideas....

// Your thread accesses the form via a variable named 'Form2'
// The 'Form2' variable below is local to the function and hence 
// hides the intended 'Form2' variable i.e. the correct 'Form2' does 
// not get assigned to anything.
TForm2 *Form2 = new TForm2(this);  
Form2->ShowModal();
Reputation Points: 1105
Solved Threads: 389
Posting Virtuoso
mitrmkar is offline Offline
1,714 posts
since Nov 2007
May 22nd, 2008
0

Re: Any Ideas....

He he..
Stupid bug..
mitmkar has already explained it. Check out http://www.functionx.com/cppcli/variables/Lesson22.htm if still not clear.
PS: To catch such bugs in future, check the compiler option to increase the warning level. In Sun workshop it was +w2. RTM.
Better way is to use lint (http://www.splint.org/win32.html) though.

Totally unrelated to the problem cheat sheet for Turbo C++ found while looking for compiler guide.. http://www.sff.net/people/brian-lars...0turbo%20c.htm
Reputation Points: 254
Solved Threads: 74
Practically a Posting Shark
thekashyap is offline Offline
804 posts
since Feb 2007
May 22nd, 2008
0

Re: Any Ideas....

Click to Expand / Collapse  Quote originally posted by BAEdwards ...
As to the initialisation state of Form2 and Memo I am not sure how I would go about checking this. I assumed that as objects are created on the form at design time, they would initialised in exactly the same way irrespective of whether the form they are associated with is dynamically created or automatically created when the program runs. Is this not the case?

How would I go about checking the initialisation state of Form2 and Memo1 etc so I can determine whether any difference arises as the result of the different ways of creating the form? Any further help would be much appreciated.
Couldn't help commenting: So a good practice is to initialize all your pointers to NULL (or 0) in c'tor (OR assign a valid address).
Also set it back to NULL once the object to which points to is deleted. Usually d'tor.
If you always ensure that you do this, you can always check anywhere in the code: if your pointer is NULL then it's not initialized correctly, else it's usable.

If you don't initialize it the problem is it'll contain junk value and if you're really unlucky it might even work !
Reputation Points: 254
Solved Threads: 74
Practically a Posting Shark
thekashyap is offline Offline
804 posts
since Feb 2007

This thread is more than three months old

No one has posted to this discussion for at least three months. Please let old threads die and do not reply to them unless you feel you have something new and valuable to contribute that absolutely must be added to make the discussion complete. Otherwise, please start a new thread in this forum instead.
Message:
Previous Thread in C++ Forum Timeline: what else cout<<??
Next Thread in C++ Forum Timeline: just in case you wanted to know





About Us | Contact Us | Advertise | Acceptable Use Policy
Forum Index | Build Custom RSS Feed


Follow us on Twitter


© 2011 DaniWeb® LLC