This document lists some of the known bugs:

* X509_Store doesn't scale too well; some of the algorithms used are O(n^2),
  where n is the number of certificates stored. Since typically n < 100, this
  is not totally fatal, but it could certainly do with some improvement.

* Due to compatability issues with RedHat's gcc 2.96 compiler, std::vector
  accesses are done using [] instead of at(). This is generally OK (we are only
  *supposed* to read valid indexes), but at times bugs have caused it so that
  an invalid index is accessed, which is either not noticed until later, or
  causes a SIGSEGV on the spot.

  Other GCC related problems: we can't use std::is* or std::to* because GCC pre
  3.0 (including RedHat's 2.96) barfs on it. And std::string is missing the
  clear() function (this is not a real problem, just an annoyance).

* Some places (mostly in the decoder) assume that the ASN.1 type tag is <= 30
  This is actually fairly easy to fix but because so few ASN.1 constructs
  actually use tags > 30 I haven't bothered to support it.

* X509_Time::X509_Time(u64bit) is not thread safe (it uses gmtime).
  Unfortunately we can't really rely on gmtime_r being available. The window
  of contention is minimal (we copy the return value into a buffer allocated on
  the stack) but it is there. If you're very paranoid about this, edit the
  get_tm function in asn1_tm.cpp to use gmtime_r

* There are various low-level threading issues, but mostly in places where a
  threaded program should not be touching things (set_mutex_type, for example).

* I'm using friend injection (ie declaring a friend class without a declaration
  or forward declaration being present). This isn't actually valid C++, but all
  the compilers I've tried Botan on accept it without any problems, so I'm not
  feeling too ambitous about fixing it. If you run into a compiler that doesn't
  accept it, let me know and I'll fix it.

* The Hardware_Timer classes (currently just RDTSC on x86 but there are similar
  instructions on other systems that will be supported eventually) have a
  problem. On most or all of the CPUs supporting such instructions, it's
  possible to make them inaccessible to user-space. In this case, we will
  receive SIGILL (on Unix) or probably some other fatal exception on other
  systems. It's possible to work around this by catching SIGILL, etc, but it's
  a really awful solution all around (not portable to boot).

* Several places assume ASCII characters. Particularly, we assume certain
  values for the character codes of 'A'-'Z', 'a'-'z', '0'-'9', '+', and
  '/'. Most of these are only for Base64 encoding/decoding, but '0'-'9', in
  particular, is somewhat more entrenched. For major culprits, look in hex.cpp,
  base64.cpp, and enc_tab.cpp.

  On a related note, big_code.cpp:decode assumes that the characters '0'
  through '9' have contiguous and increasing values, but does not assume any
  particular value. The functions to_string and to_u32bit (in util.cpp) also
  have this property.

  I really don't know what to do about this, if anything. If anyone out there
  is still actually using an EBCDIC machine and would like to help port Botan
  to MVS or OS/400 or something, send me an email. Otherwise, I doubt I'll ever
  worry about it. I don't like that it's dependent on the character set, but at
  the same time, virtually nobody uses a character set that isn't "like" ASCII,
  at least from this limited view.

  Another nasty thing is that while the encoders will encode into the native
  character set, the decoders will not; they will only accept ASCII chars.
  This can mostly be prevented by generating these tables at run time. Then,
  the encoders and decoders will accept native character set, but not others.

  ALSO: The new X.509 stuff is all wrong on non-ASCII systems. A number of the
  common ASN.1 types (NumericString, PrintableString, UTCTime, etc) are encoded
  as ASCII (or ASCII superset) strings. The code needs to support conversion
  for systems where the native char set is not an ASCII superset.

* There is a nasty little problem with the build system. Namely, because we
  pass -Iinclude, some (most? all?) compilers will look in the include/
  directory before looking in /usr/include, etc. This can cause conflicts, when
  a header in /usr/include #include's something like 'mutex.h', expecting to
  get /usr/include/mutex.h, but instead gets the library's mutex.h.

  Thankfully this only affects building, applications aren't bothered by this
  (since they use the standard include paths). It should be fixed, but I'm not
  a sufficient make wizard to figure out how to do so. It's a really stupid
  problem, considering that our code doesn't even want to see the headers as
  <header.h>; all it wants is <botan/header.h>
