Dangerous convertion?

Discussion in 'C Programming' started by mark, Aug 9, 2009.

  1. mark

    mark Guest

    Hello Friends ~~

    I want to convert CString to LPBYTE like
    LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    is it very dangerous to do that?

    Thanks.
     
    mark, Aug 9, 2009
    #1
    1. Advertising

  2. mark wrote:
    > [...]
    > I want to convert CString to LPBYTE like
    > LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    > is it very dangerous to do that?


    I guess your question is about Microsoft's C++ class library.
    1. comp.lang.c++ is probably a better place to ask about that.
    2. If all else fails, read the manual.

    http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx

    --
    Brüder, in die Tonne die Freiheit,
    Brüder, ein Stoppschild davor.
    Egal was die Schwarzen Verlangen
    Rufen wir: Ja! Brav im Chor.
     
    Alexander Bartolich, Aug 9, 2009
    #2
    1. Advertising

  3. mark

    mark Guest

    anyone?

    mark wrote:
    > Hello Friends ~~
    >
    > I want to convert CString to LPBYTE like
    > LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    > is it very dangerous to do that?
    >
    > Thanks.
     
    mark, Aug 9, 2009
    #3
  4. On 9 Aug, 12:16, Alexander Bartolich <>
    wrote:
    > mark wrote:
    > > [...]
    > > I want to convert CString to LPBYTE like
    > > LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    > > is it very dangerous to do that?

    >
    > I guess your question is about Microsoft's C++ class library.
    > 1. comp.lang.c++ is probably a better place to ask about that.


    nonono!! As you say this is MS stuff. And therefore it is just
    as off-topic on comp.lang.c++ asit is on comp.lang.c.

    > 2. If all else fails, read the manual.
    >
    > http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx


    this is good advice. Then try a microsoft newsgroup
     
    Nick Keighley, Aug 9, 2009
    #4
  5. mark

    Tom St Denis Guest

    On Aug 9, 7:16 am, Alexander Bartolich <>
    wrote:
    > mark wrote:
    > > [...]
    > > I want to convert CString to LPBYTE like
    > > LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    > > is it very dangerous to do that?

    >
    > I guess your question is about Microsoft's C++ class library.
    > 1. comp.lang.c++ is probably a better place to ask about that.
    > 2. If all else fails, read the manual.
    >
    > http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx


    The recommended method on the page is all that's wrong with msft...

    CString aCString = "A string";
    char myString[256];
    strcpy(myString, (LPCTSTR)aString);

    Can the kids spot the problem with this code?

    Tom
     
    Tom St Denis, Aug 9, 2009
    #5
  6. mark

    James Kuyper Guest

    mark wrote:
    > anyone?
    >
    > mark wrote:
    >> Hello Friends ~~
    >>
    >> I want to convert CString to LPBYTE like
    >> LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    >> is it very dangerous to do that?
    >>
    >> Thanks.


    According to my news server, the first response to your original message
    was sent 8 minutes before you sent this one; but I suppose it might not
    have propagated to your news server yet.

    Usenet is not a chat room. Don't expect an immediate response. The best
    response to your question might come from someone who might be asleep at
    the time you sent it. As a general rule, wait at least 24 hours before
    assuming that you've been ignored.
     
    James Kuyper, Aug 9, 2009
    #6
  7. mark

    Eric Sosman Guest

    Tom St Denis wrote:
    > On Aug 9, 7:16 am, Alexander Bartolich <>
    > wrote:
    >> mark wrote:
    >>> [...]
    >>> I want to convert CString to LPBYTE like
    >>> LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    >>> is it very dangerous to do that?

    >> I guess your question is about Microsoft's C++ class library.
    >> 1. comp.lang.c++ is probably a better place to ask about that.
    >> 2. If all else fails, read the manual.
    >>
    >> http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx

    >
    > The recommended method on the page is all that's wrong with msft...
    >
    > CString aCString = "A string";
    > char myString[256];
    > strcpy(myString, (LPCTSTR)aString);
    >
    > Can the kids spot the problem with this code?


    Three undeclared identifiers and an executable statement
    not inside a function block.

    --
    Eric Sosman
    lid
     
    Eric Sosman, Aug 9, 2009
    #7
  8. mark

    Tom St Denis Guest

    On Aug 9, 8:36 am, Eric Sosman <> wrote:
    > Tom St Denis wrote:
    > > On Aug 9, 7:16 am, Alexander Bartolich <>
    > > wrote:
    > >> mark wrote:
    > >>> [...]
    > >>> I want to convert CString to LPBYTE like
    > >>> LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    > >>> is it very dangerous to do that?
    > >> I guess your question is about Microsoft's C++ class library.
    > >> 1. comp.lang.c++ is probably a better place to ask about that.
    > >> 2. If all else fails, read the manual.

    >
    > >>http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx

    >
    > > The recommended method on the page is all that's wrong with msft...

    >
    > > CString aCString = "A string";
    > > char myString[256];
    > > strcpy(myString, (LPCTSTR)aString);

    >
    > > Can the kids spot the problem with this code?

    >
    >      Three undeclared identifiers and an executable statement
    > not inside a function block.


    Well letting aside it's not a complete program [I wouldn't fault msft
    for that], it has the potential for a buffer overflow. But given you
    didn't point that out I guess you didn't see that either...

    I know this is clc and all, but come on, if you didn't see that...
     
    Tom St Denis, Aug 9, 2009
    #8
  9. Tom St Denis <> writes:

    > On Aug 9, 8:36 am, Eric Sosman <> wrote:
    >> Tom St Denis wrote:
    >> > On Aug 9, 7:16 am, Alexander Bartolich <>
    >> > wrote:
    >> >> mark wrote:
    >> >>> [...]
    >> >>> I want to convert CString to LPBYTE like
    >> >>> LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    >> >>> is it very dangerous to do that?
    >> >> I guess your question is about Microsoft's C++ class library.
    >> >> 1. comp.lang.c++ is probably a better place to ask about that.
    >> >> 2. If all else fails, read the manual.

    >>
    >> >>http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx

    >>
    >> > The recommended method on the page is all that's wrong with msft...

    >>
    >> > CString aCString = "A string";
    >> > char myString[256];
    >> > strcpy(myString, (LPCTSTR)aString);

    >>
    >> > Can the kids spot the problem with this code?

    >>
    >>      Three undeclared identifiers and an executable statement
    >> not inside a function block.

    >
    > Well letting aside it's not a complete program [I wouldn't fault msft
    > for that], it has the potential for a buffer overflow.


    But the buffer overflow possibility comes from what Eric pointed out.
    if the example had been correct there would be no buffer overflow,
    surely?

    > But given you
    > didn't point that out I guess you didn't see that either...


    Did you spot the error that Eric pointed out by saying three (rather
    than two) undeclared identifiers? If you did it seems odd to call the
    problem "potential buffer overflow" though, of course, depending on
    what aString is that is indeed a possibility.

    > I know this is clc and all, but come on, if you didn't see that...


    I think he did.

    --
    Ben.
     
    Ben Bacarisse, Aug 9, 2009
    #9
  10. mark

    Eric Sosman Guest

    Tom St Denis wrote:
    > On Aug 9, 8:36 am, Eric Sosman <> wrote:
    >> Tom St Denis wrote:
    >>> On Aug 9, 7:16 am, Alexander Bartolich <>
    >>> wrote:
    >>>> mark wrote:
    >>>>> [...]
    >>>>> I want to convert CString to LPBYTE like
    >>>>> LPBYTE lpByte = (BYTE*)(LPCTSTR)cstring;
    >>>>> is it very dangerous to do that?
    >>>> I guess your question is about Microsoft's C++ class library.
    >>>> 1. comp.lang.c++ is probably a better place to ask about that.
    >>>> 2. If all else fails, read the manual.
    >>>> http://msdn.microsoft.com/en-us/library/awkwbzyc.aspx
    >>> The recommended method on the page is all that's wrong with msft...
    >>> CString aCString = "A string";
    >>> char myString[256];
    >>> strcpy(myString, (LPCTSTR)aString);
    >>> Can the kids spot the problem with this code?

    >> Three undeclared identifiers and an executable statement
    >> not inside a function block.

    >
    > Well letting aside it's not a complete program [I wouldn't fault msft
    > for that], it has the potential for a buffer overflow. But given you
    > didn't point that out I guess you didn't see that either...
    >
    > I know this is clc and all, but come on, if you didn't see that...


    Actually, what I failed to see was a *fourth* undeclared
    identifier.

    More seriously, I really, truly, have nothing but guesses
    about what a `CString' may be, and no notion at all about the
    meaning of `LPCTSTR'. I imagine they're C++-isms, but I know
    nothing of C++; for whatever rational or irrational reason I
    have succeeded in avoiding it just as I've avoided COBOL. If
    I were interested in C++ (as many perfectly decent people are),
    I'd be reading a C++ forum.

    --
    Eric Sosman
    lid
     
    Eric Sosman, Aug 9, 2009
    #10
  11. mark

    Tom St Denis Guest

    On Aug 9, 9:52 am, Eric Sosman <> wrote:
    >      More seriously, I really, truly, have nothing but guesses
    > about what a `CString' may be, and no notion at all about the
    > meaning of `LPCTSTR'.  I imagine they're C++-isms, but I know
    > nothing of C++; for whatever rational or irrational reason I
    > have succeeded in avoiding it just as I've avoided COBOL.  If
    > I were interested in C++ (as many perfectly decent people are),
    > I'd be reading a C++ forum.


    Look, I'll break it down for you.

    You should never use strcpy. Ever. It's a bad habit to get in.

    Specially in a generic example showing how to copy from some type to
    another because you know people will copy/paste it into their
    applications.

    My point was that leaving aside it's an incomplete program because
    it's just a snippet, it shows that MSFT can't even write a damn string
    copy example without doing it wrong.

    BTW, the fact that it's a snippet and not a complete program is fine
    IMHO. They're just showing how to use the API to perform an
    operation, not how to write an entire program that does the
    operation. So the fact that you're harping has motivations that elude
    me.

    Tom
     
    Tom St Denis, Aug 9, 2009
    #11
  12. mark

    Eric Sosman Guest

    Tom St Denis wrote:
    >
    > You should never use strcpy. Ever. It's a bad habit to get in.


    "Nonsense," "nonsense," and "too late."

    My principal objection to strcpy() has nothing to do with
    safety -- it's perfectly safe when "used as directed" -- but
    the same objection I have to all forms of copying: Making a
    copy of something you already know does not increase what is
    known. It doesn't "advance the state of the computation," it
    doesn't move the program closer to a goal or solution. When
    I'm considering making a copy of something, I ponder whether
    it's avoidable, whether the reason for copying is a good one.
    Then if the reason is in fact good, I go ahead and make the
    copy. Using strcpy(), if the thing being copied is a string,
    because it's the right tool for the job. In responsible hands,
    anyhow.

    --
    Eric Sosman
    lid
     
    Eric Sosman, Aug 9, 2009
    #12
  13. mark

    Tom St Denis Guest

    On Aug 9, 10:29 am, Eric Sosman <> wrote:
    > Tom St Denis wrote:
    >
    > > You should never use strcpy.  Ever.  It's a bad habit to get in.

    >
    >      "Nonsense," "nonsense," and "too late."
    >
    >      My principal objection to strcpy() has nothing to do with
    > safety -- it's perfectly safe when "used as directed" -- but
    > the same objection I have to all forms of copying: Making a
    > copy of something you already know does not increase what is
    > known.  It doesn't "advance the state of the computation," it
    > doesn't move the program closer to a goal or solution.  When
    > I'm considering making a copy of something, I ponder whether
    > it's avoidable, whether the reason for copying is a good one.
    > Then if the reason is in fact good, I go ahead and make the
    > copy.  Using strcpy(), if the thing being copied is a string,
    > because it's the right tool for the job.  In responsible hands,
    > anyhow.


    While I agree blanket "never use X" statements are nonsense, for
    example, there are plenty of good uses for goto, strcpy is one that
    just should be avoided.

    It's the sort of bad habits that lead to other things like

    - not checking parameters for validity
    - not checking returns of malloc/calloc
    - Not checking boundaries

    How often does "malloc" really fail? So I guess checking the return
    is just paranoia, etc. Sometimes not being lazy up front saves having
    to go back and fix things later when it costs more to re-open the
    code.

    As for never having a use for making a copy, sometimes you're
    transferring it from one structure to another and you're not at a
    point to know where the pointers came from [stack, heap, auto, ???] so
    you can't just copy the pointer.

    Tom
     
    Tom St Denis, Aug 9, 2009
    #13
  14. mark

    Tom St Denis Guest

    On Aug 9, 11:42 am, Richard Heathfield <> wrote:
    > Tom St Denis said:
    >
    > <snip>
    >
    > > You should never use strcpy.

    >
    > Why not? And what would you recommend in its place?


    strncpy and/or write your own that checks bounds.

    Sure you *can* safely use strcpy, but it's a better habit to use
    functions or write code that honour boundaries instead.

    Tom
     
    Tom St Denis, Aug 9, 2009
    #14
  15. mark

    Eric Sosman Guest

    Tom St Denis wrote:
    > On Aug 9, 10:29 am, Eric Sosman <> wrote:
    >> Tom St Denis wrote:
    >>
    >>> You should never use strcpy. Ever. It's a bad habit to get in.

    >> "Nonsense," "nonsense," and "too late."
    >>
    >> My principal objection to strcpy() has nothing to do with
    >> safety -- it's perfectly safe when "used as directed" -- but
    >> the same objection I have to all forms of copying: Making a
    >> copy of something you already know does not increase what is
    >> known. It doesn't "advance the state of the computation," it
    >> doesn't move the program closer to a goal or solution. When
    >> I'm considering making a copy of something, I ponder whether
    >> it's avoidable, whether the reason for copying is a good one.
    >> Then if the reason is in fact good, I go ahead and make the
    >> copy. Using strcpy(), if the thing being copied is a string,
    >> because it's the right tool for the job. In responsible hands,
    >> anyhow.

    >
    > While I agree blanket "never use X" statements are nonsense, for
    > example, there are plenty of good uses for goto, strcpy is one that
    > just should be avoided.
    >
    > It's the sort of bad habits that lead to other things like
    >
    > - not checking parameters for validity
    > - not checking returns of malloc/calloc
    > - Not checking boundaries


    Using strcpy() is the cause of these bad habits? Can you
    quote any research to support this claim, or is it just one of
    those "Stop, or you'll go blind" things?

    The act of calling strcpy(), or even the intent thereof,
    does not prompt me to swallow untrusted values from untrusted
    sources. Nor does it influence me to omit tests for malloc()
    failure. I *do* omit boundary checking, because there's no
    need: I allocate sufficient space before copying, and once
    the space is known to suffice there's no reason to check it.

    > How often does "malloc" really fail? So I guess checking the return
    > is just paranoia, etc. Sometimes not being lazy up front saves having
    > to go back and fix things later when it costs more to re-open the
    > code.


    If this has anything at all to do with strcpy(), I am
    unable to discern the connection.

    > As for never having a use for making a copy, sometimes you're
    > transferring it from one structure to another and you're not at a
    > point to know where the pointers came from [stack, heap, auto, ???] so
    > you can't just copy the pointer.


    Yes, I know -- and I *did* say that copying is sometimes
    necessary. Often you want a copy as an "initializer" for an
    object you will then proceed to modify, but you'd like the
    original to remain intact. Sometimes the original is itself
    in jeopardy, sitting in a soon-to-vanish auto array or in a
    soon-to-be-overwritten I/O buffer. And sometimes the point
    of copying isn't to create redundant data but to rearrange,
    as in sorting an array.

    ... and when a string is the thing you want to copy,
    strcpy() is just the ticket.

    --
    Eric Sosman
    lid
     
    Eric Sosman, Aug 9, 2009
    #15
  16. "Malcolm McLean" <> writes:
    > "Richard Heathfield" <> wrote in message news
    >> Malcolm McLean said:
    >>> "Tom St Denis" <> wrote in message
    >>>>
    >>>>How often does "malloc" really fail?
    >>>>
    >>> On a computer with 2GB of memory, an allocation of 100 bytes will
    >>> have a 0.0000005 chance of being the culprit if the computer runs
    >>> out of memory.

    >>
    >> 2GB / 100 = 21474836 (ish). How long does it take to perform twenty+
    >> million allocations? Not long, nowadays.
    >>

    > That's the wrong way of looking at it.


    I think it's exactly the right way of looking at it.

    > As we all know by now, banks can fail. Say you've got an account at
    > the high street bank Boorcloys (fictitious name to avoid libel
    > charges). You withdraw a hundred pounds. What's the chance that your
    > transaction will fail because the bank has run out of money at that
    > point?
    > Millions of transactions a day are putting money into and out of the
    > bank, but eventually if withdrawls exceed deposits the bank will run
    > out of money. However this is highly embarrassing for the
    > government, so action is taken when banks start to fail too often -
    > more liquidity is injected. You can't have a situation where the
    > bank is failing every few days, because no-one would tolerate it.


    Computers are not banks. The analagous statement that you can't
    have a situation where the computer is failing every few days,
    because no-one would tolerate it, is inconsistent with reality;
    many computers *do* fail every few days, and people *do* tolerate it.

    Failing to check malloc isn't like making a small withdrawal from
    the bank, it's like the bank not bothering to check whether your
    withdrawal is for more money than the bank has and ignoring the
    consequences.

    Adding code to check the result of malloc() is easier than computing
    the probability that you can get away without checking it.

    --
    Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
    Nokia
    "We must do something. This is something. Therefore, we must do this."
    -- Antony Jay and Jonathan Lynn, "Yes Minister"
     
    Keith Thompson, Aug 9, 2009
    #16
  17. mark

    James Kuyper Guest

    Malcolm McLean wrote:
    > "Richard Heathfield" <> wrote in message news
    >> Malcolm McLean said:
    >>
    >>> "Tom St Denis" <> wrote in message
    >>>> How often does "malloc" really fail?
    >>>>
    >>> On a computer with 2GB of memory, an allocation of 100 bytes will
    >>> have a 0.0000005 chance of being the culprit if the computer runs
    >>> out of memory.

    >> 2GB / 100 = 21474836 (ish). How long does it take to perform twenty+
    >> million allocations? Not long, nowadays.
    >>

    > That's the wrong way of looking at it.
    >
    > As we all know by now, banks can fail. Say you've got an account at the high
    > street bank Boorcloys (fictitious name to avoid libel charges). You withdraw
    > a hundred pounds. What's the chance that your transaction will fail because
    > the bank has run out of money at that point?


    The chance of your transaction failing can be estimated by methods
    similar to those given above, if you decided to make your withdrawal at
    the same time and for the same reason as a lot of other people. This is
    called a "run on the bank". They used to be quite common, and the fact
    that they're less common nowadays is because a great deal of effort has
    been expended to set up a legal and regulatory system to prevent them
    from happening. It's a primarily psychological issue that has no analog
    in memory allocation.

    On the other hand, banking is a bad analogy for a different reason. A
    depositor has no right to remove any more money from a bank than the
    current account balance, and interest rates give depositors an incentive
    to take out no more than they actually need. In memory allocation,
    here's no corresponding limit, and no corresponding incentive, to
    restrain memory allocation requests. Therefore, the chance that a given
    request might make the system will run out of memory can, to a rough
    first approximation, be estimated by methods similar to those given above.
     
    James Kuyper, Aug 9, 2009
    #17
  18. mark

    bartc Guest

    "Keith Thompson" <> wrote in message
    news:...
    > "Malcolm McLean" <> writes:
    >> "Richard Heathfield" <> wrote in message news
    >>> Malcolm McLean said:
    >>>> "Tom St Denis" <> wrote in message
    >>>>>
    >>>>>How often does "malloc" really fail?
    >>>>>
    >>>> On a computer with 2GB of memory, an allocation of 100 bytes will
    >>>> have a 0.0000005 chance of being the culprit if the computer runs
    >>>> out of memory.
    >>>
    >>> 2GB / 100 = 21474836 (ish). How long does it take to perform twenty+
    >>> million allocations? Not long, nowadays.
    >>>

    >> That's the wrong way of looking at it.

    >
    > I think it's exactly the right way of looking at it.
    >
    >> As we all know by now, banks can fail. Say you've got an account at
    >> the high street bank Boorcloys (fictitious name to avoid libel
    >> charges). You withdraw a hundred pounds. What's the chance that your
    >> transaction will fail because the bank has run out of money at that
    >> point?


    > Computers are not banks. The analagous statement that you can't
    > have a situation where the computer is failing every few days,
    > because no-one would tolerate it, is inconsistent with reality;
    > many computers *do* fail every few days, and people *do* tolerate it.
    >
    > Failing to check malloc isn't like making a small withdrawal from
    > the bank, it's like the bank not bothering to check whether your
    > withdrawal is for more money than the bank has and ignoring the
    > consequences.


    A better analogy is when you give the OS your own reserves of memory on
    'deposit'. The OS then lends this memory to other, 'sub-prime' processes
    which don't give it back (eg. badly written C applications). Then when you
    want to make use of your own, personal memory, it's not available.

    --
    bartc
     
    bartc, Aug 9, 2009
    #18
  19. mark

    Phil Carmody Guest

    Tom St Denis <> writes:
    > On Aug 9, 11:42 am, Richard Heathfield <> wrote:
    >> Tom St Denis said:
    >>
    >> <snip>
    >>
    >> > You should never use strcpy.

    >>
    >> Why not? And what would you recommend in its place?

    >
    > strncpy and/or write your own that checks bounds.


    I view strncpy as a bigger threat to sanity than strcpy. It has
    the illusion of taking a few extra things into account, but it
    less efficient and invites pointers later in program execution
    to wander off into UB-land. strlcpy is what strncpy should have
    been.

    Phil
    --
    If GML was an infant, SGML is the bright youngster far exceeds
    expectations and made its parents too proud, but XML is the
    drug-addicted gang member who had committed his first murder
    before he had sex, which was rape. -- Erik Naggum (1965-2009)
     
    Phil Carmody, Aug 9, 2009
    #19
  20. mark

    Eric Sosman Guest

    Richard Heathfield wrote:
    > [...]
    > As with any function, before calling it, one should ensure that it is
    > safe to call.


    There's the crux, I think. memcpy() is unsafe if either
    the source or destination is smaller than the count. longjmp()
    is unsafe if the caller of setjmp() has already returned. Even
    printf("Hello, %s!\n", placeName) is unsafe if there's no '\0'
    within the memory pointed to by `placeName'.

    "Safe when used as directed" (not intended as a plug for
    "Ubik," but I can't see the phrase without recalling the book)
    is the watchword. Ignoring the directions is what makes the
    trouble: It's not aspirin's fault if you swallow an entire bottle
    of the stuff. One could even argue, rather speciously, that
    gets() is "safe when used as directed," but that the directions
    ("First, foretell the future") are not easy to follow.

    As a defense against thoughtless programmers, the strlcpy()
    and strlcat() functions (not part of the Standard library) show
    promise, I think. They're not inherently safer than strcpy()
    and strcat() -- it is *always* possible to pass an incorrect
    output area size -- but at least it forces the T.P. to think
    about that size, if only for a moment. Not enough in and of
    itself, but a moment's thought is better than none.

    --
    Eric Sosman
    lid
     
    Eric Sosman, Aug 9, 2009
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Replies:
    8
    Views:
    1,904
    Mike Treseler
    Feb 10, 2005
  2. isore
    Replies:
    0
    Views:
    538
    isore
    Jul 1, 2004
  3. Hiranya Samarasekera

    BMP to GIF convertion

    Hiranya Samarasekera, Aug 26, 2003, in forum: Java
    Replies:
    3
    Views:
    2,558
    Marco Schmidt
    Aug 27, 2003
  4. cccc
    Replies:
    8
    Views:
    10,037
    Andrew Thompson
    Sep 21, 2004
  5. Replies:
    6
    Views:
    383
    red floyd
    May 30, 2008
Loading...

Share This Page