Apache 2.0 Thread Safety Issues
Copyright 2006 The Apache Software Foundation.
Licensed under the Apache License, Version 2.0
Korean Translator: ±èÁ¤±Õ <http://oops.org>
¹ø¿ªº» Âü°í »çÇ×
Apache 2.0 ¿¡¼ ¾î¶² ¾²·¹µå mpm À» »ç¿ëÇÒ °æ¿ì, Apache ¿¡¼ È£ÃâµÇ´Â ¸ðµç ÇÔ¼ö°¡ thread safe ÇØ¾ß ÇÏ´Â °ÍÀº »ó´çÈ÷ Áß¿äÇÑ ÀÏÀÔ´Ï´Ù. 3th party extension ÀÌ ¸µÅ©(link)µÇ¾úÀ» °æ¿ì, ¼¹ö°¡ thread safe ÇÑ °á°ú¸¦ °¡Áø´Ù°í ¸»Çϱâ´Â ÈûÀÌ µì´Ï´Ù. ÀÌ ¹®Á¦´Â °úÁßÇÑ ·Îµå°¡ °É·Á¾ß ÇÏ°í, ¾î¶² »óÅ¿¡¼ ³ªÅ¸³¯Áö ¸ð¸£´Â ¹Ì¹¦ÇÑ race condition °ú °°ÀÌ ¹ß»ýÇϱ⠶§¹®¿¡, ÀϹÝÀûÀ¸·Î ÀϽÃÀûÀÎ Å×½ºÆ®·Î´Â thread safe ÇÏ´Ù°í ¸»ÇÒ ¼ö´Â ¾ø½À´Ï´Ù.
1. Àü¿ª º¯¼ö¿Í Á¤Àû º¯¼ö ¶¸ðµâÀ» ÀÛ¼ºÇÏ·Á°í Çϰųª, ¸ðµâ ¶Ç´Â 3rd party ¶óÀ̺귯¸®°¡ thread safe ÇÏ´Ù°í °áÁ¤À» ÇÏ·Á ÇÒ ¶§, À¯ÀÇÇÒ ÀϵéÀÌ ÀÖ½À´Ï´Ù.
¸ÕÀú, °¢ °³º° thread °¡ ÀڽŸ¸ÀÇ ÇÁ·Î±×·¥ counter, stack, register ¸¦ °¡Áö°í ÀÖ´Â thread ¸ðµ¨ÀÎÁö È®ÀÎÇÒ ÇÊ¿ä°¡ ÀÖ½À´Ï´Ù. ·ÎÄà º¯¼öµéÀº stack ¿¡ ÀúÀåÀÌ µÇ±â ¶§¹®¿¡ ¹®Á¦°¡ ¾ø½À´Ï´Ù. ÇÏÁö¸¸, ¾î¶² Á¤Àû º¯¼ö³ª Àü¿ª º¯¼ö´Â ÁÖÀÇÇؾßÇÒ ÇÊ¿ä°¡ ÀÖ½À´Ï´Ù. ÀÌ´Â Àý´ëÀûÀ¸·Î Á¤Àû ¶Ç´Â Àü¿ª º¯¼ö¸¦ »ç¿ëÇÏÁö ¸»¾Æ¾ß ÇÑ´Ù´Â °ÍÀº ¾Æ´Õ´Ï´Ù. ¾î¶² º¯¼ö°¡ ¸ðµç thread ¿¡ ¿µÇâÀ» ¹ÌÄ¡±â¸¦ ¿øÇÏ´Â °æ¿ì°¡ ÀÖÀ» ¼ö ÀÖ½À´Ï´Ù. ÇÏÁö¸¸ ÀϹÝÀûÀ¸·Î ´ç½ÅÀÇ Äڵ尡 thread safe Çϱ⸦ ¹Ù¶õ´Ù¸é, ÀÌ º¯¼ö¸¦ Á¤Àû/Àü¿ª º¯¼ö·Î »ç¿ëÇÏ´Â °ÍÀ» ÇÇÇÏ´Â °ÍÀÌ ÁÁ½À´Ï´Ù.
ÇÁ·Î±×·¥ Àüü¿Í ¸ðµç thrad ¿¡¼ Á¢±ÙÀ» ÇÒ ÇÊ¿ä°¡ ÀÖ´Â Àü¿ª º¯¼ö°¡ ÀÖÀ» °æ¿ì, ÀÌ º¯¼ö¸¦ ¾÷µ¥ÀÌÆ® ÇÔ¿¡ ÀÖ¾î ´ë´ÜÈ÷ ÁÖÀÇÇØ¾ß ÇÕ´Ï´Ù. ¿¹¸¦ µé¾î, counter ¸¦ Áõ°¡ ½ÃÅ°´Â º¯¼ö¶ó¸é, ´Ù¸¥ thread ¿¡ race condition À» ÇÇÇϱâ À§ÇÏ¿© ÃÖ¼ÒÇÑÀ¸·Î(atomically) Áõ°¡¸¦ ½ÃÄÑ¾ß ÇÒ ¼öµµ ÀÖ½À´Ï´Ù. ´ç½ÅÀº mutex (mutual exclustion)¸¦ ÀÌ¿ëÇÏ¿© ÀÌ°ÍÀ» ÇÒ ¼ö ÀÖ½À´Ï´Ù. mutex ¿¡ ¶ôÀ» °É°í, ÇöÀç °ªÀ» Àаí, ±× º¯¼ö¸¦ Áõ°¡ ½ÃŲ ÈÄ¿¡ ¾²°í, mutex ÀÇ ¶ôÀ» ÇØÁ¦ ÇϽʽÿÀ. °ªÀ» º¯°æÇϱ⸦ ¿øÇÏ´Â ´Ù¸¥ ¾î¶² thread ´Â º¯¼ö°¡ Ŭ¸®¾î µÉ ¶§±îÁö ¸ÕÀú mutex ¸¦ °Ë»çÇÏ°í ºí·° ½ÃÄÑ¾ß ÇÕ´Ï´Ù.
¸¸¾à APRÀ» »ç¿ëÇÏ°í ÀÖ´Ù¸é, apr_atomic_* ÇÔ¼ö¿Í apr_thread_mutex_* ÇÔ¼ö¸¦ ÂüÁ¶ ÇϽʽÿÀ.
2. errno ¶errno ´Â ¸¶Áö¸·À¸·Î ¹ß»ýÇÑ ¿¡·¯ÀÇ ¿¡·¯ ¹øÈ£¸¦ °¡Áö°í ÀÖ´Â Àü¿ª º¯¼ö ÀÔ´Ï´Ù. ÇϳªÀÇ ¾²·¹µå°¡ errno ¸¦ ¼³Á¤ÇÏ´Â low-level ÇÔ¼ö¸¦ È£ÃâÇÏ¿´°í, ´Ù¸¥ ¾²·¹µå°¡ ÀÌ º¯¼ö¸¦ ÂüÁ¶ ÇÏ¿´À» °æ¿ì, ÂüÁ¶ÇÑ ¾²·¹µå·Î ¿øÄ¡¾Ê´Â errno ¸¦ Àü´ÞÇÏ°Ô µË´Ï´Ù. ÀÌ ¹®Á¦¸¦ ÇØ°áÇϱâ À§ÇÏ¿©, ¸ðµâ°ú ¶óÀ̺귯¸®¿¡ _REENTRANT »ó¼ö¸¦ ¼±¾ðÇϰųª ¶Ç´Â ÄÄÆÄÀÏ ½Ã¿¡ -D_REENTRANT ¿É¼ÇÀ» ÁÖ½Ç ¼ö ÀÖ½À´Ï´Ù. ÀÌ »ó¼ö´Â errno ¸¦ per-thread º¯¼ö·Î ¸¸µé¾î ÁÖ¸ç, Äڵ带 Åõ¸íÇÏ°Ô ÇÒ ¼ö ÀÖ½À´Ï´Ù. ÀÌ »ó¼ö¸¦ ¼±¾ðÇÏ´Â °ÍÀº ´ÙÀ½°ú °°ÀÌ ÀÛµ¿À» Çϵµ·Ï ÇÕ´Ï´Ù:
#define errno (*(__errno_location()))
ÀÌ ÄÚµåÀÇ Àǹ̴ errono ¿¡ Á¢±ÙÀ» Çϸé, libc ¿¡¼ Á¦°øµÇ´Â __errno_location() ÀÌ È£ÃâÀÌ µË´Ï´Ù. _REENTRANT ¸¦ ¼³Á¤Çϸé, µ¿µîÇÑ ±â´ÉÀ» °¡Áø *_r ÇÔ¼ö¸¦ Á¦°øÇÒ °æ¿ì °Á¦·Î ÀÌ ÇÔ¼öµé·Î ÀçÁ¤ÀÇ ÇÕ´Ï´Ù. ±×¸®°í °¡²û ¾ÈÀüÇÑ ÇÔ¼ö È£ÃâÀ» À§ÇØ getc/pubc ¸ÅÅ©·Î¸¦ º¯°æÇϱ⵵ ÇÕ´Ï´Ù. _REENTRANT ¸¦ Ãß°¡ÇÏ´Â °Í ¿Ü¿¡ ÀÌ ¹®Á¦¿¡ ´ëÇÏ¿© ¿µÇâÀ» ¹ÌÄ¥¼ö ÀÖ´Â ½Éº¼·Î´Â _POSIX_C_SOURCE, _THREAD_SAFE, _SVID_SOURCE, _BSD_SOURCE µîÀÌ ÀÖ½À´Ï´Ù. ÀÌ °Í¿¡ ´ëÇؼ´Â libc ¹®¼¸¦ ÂüÁ¶ ÇϽʽÿÀ.
3. Common standard troublesome functions ¶thread safe ÇÏ°Ô ¸¸µé¾î¾ß ÇÒ »Ó ¾Æ´Ï¶ó ÀçÁøÀÔ(?..reentrant)ÀÌ °¡´É Çؾ߸¸ ÇÕ´Ï´Ù. strtok °¡ ¸íÈ®ÇÏ°Ô ÀÌ ¹®Á¦¸¦ °¡Áö°í ÀÖ½À´Ï´Ù. strtok °¡ ±â¾ïÀ» ÇÏ°í ÀÖ´Â ±¸ºÐÀÚ·Î strtok ¸¦ óÀ½ È£ÃâÀ» ÇÏ°í, °¢°¢ÀÇ ¼ö¹ÝµÇ´Â È£Ãâ¿¡ ´ÙÀ½ ÅäÅ«À» ¹ÝȯÇÏ°Ô µË´Ï´Ù. (Àǹ̸¦ Àß ¸ð¸£°Ú±º¿ä..You call it the first time with your delimiter which it then remembers and on each subsequent call it returns the next token.) tokenizing »óŸ¦ °ü¸®Çϱâ À§ÇÏ¿© ÇÔ¼ö°¡ ÀÚ½ÅÀÇ Á¤Àû ½ºÅ丮Áö ´ë½Å¿¡ »ç¿ëÇϱâ À§ÇÏ¿© ÇÒ´çµÈ char * ¸¦ Æ÷ÇÔÇÑ Æ¯º°ÇÑ ÀÎÀÚ¸¦ °¡Áø strtok_r() À̶ó°í ºÒ¸®´Â ÀçÁøÀÔ ¹öÀüÀÇ ÇÔ¼ö¸¦ °¡Áö°í ÀÖ½À´Ï´Ù. APR À» »ç¿ëÇÑ´Ù¸é, apr_strtok() ¸¦ »ç¿ëÇÒ ¼ö ÀÖ½À´Ï´Ù.
crypt() ¿ª½Ã ÀçÁøÀÔ(reentrant)ÀÌ µÇÁö ¾Ê´Â ÇÔ¼ö ÁßÀÇ Çϳª ÀÔ´Ï´Ù. ±×·¯¹Ç·Î ¶óÀ̺귯¸®¿¡ ÀÖ´Â ÀÌ ÇÔ¼ö¸¦ °¡·ÎÁú·¯¼ È£ÃâÇÏ´Â °ÍÀº ÇÇÇØ¾ß ÇÕ´Ï´Ù. ¾î¶² ½Ã½ºÅÛ¿¡¼´Â ÀçÁøÀÔÀÌ °¡´ÉÇϱ⠶§¹®¿¡, Ç×»ó ¹®Á¦°¡ µÇ´Â °ÍÀº ¾Æ´Õ´Ï´Ù. If your system has crypt_r() chances are you should be using that, or if possible simply avoid the whole mess by using md5 instead.
4. Common 3rd Party Libraries ¶´ÙÀ½Àº Apache ÀÇ 3th party ¸ðµâÀÌ »ç¿ëÇÏ°í ÀÖ´Â system ¶óÀ̺귯¸®ÀÇ ¸®½ºÆ® ÀÔ´Ï´Ù. ´ç½ÅÀÌ »ó¿ëÇÏ´Â ¸ðµâÀÌ ÀáÀç°ÅÀ¸·Î ¾ÈÀüÇÏÁö ¾ÊÀº ¶óÀ̺귯¸®¸¦ »ç¿ëÇÏ°í ÀÖ´Ù¸é, ldd(1) ³ª nm(1) °ú °°Àº µµ±¸¸¦ »ç¿ëÇÏ¿© È®ÀÎÀ» ÇÒ ¼ö ÀÖ½À´Ï´Ù. ´ÙÀ½ÀÇ ¿¹´Â PHP ¸¦ ÀÌ¿ëÇÏ¿© È®ÀÎÇÏ´Â °ÍÀÔ´Ï´Ù:
% ldd libphp4.so
libsablot.so.0 => /usr/local/lib/libsablot.so.0 (0x401f6000) libexpat.so.0 => /usr/lib/libexpat.so.0 (0x402da000) libsnmp.so.0 => /usr/lib/libsnmp.so.0 (0x402f9000) libpdf.so.1 => /usr/local/lib/libpdf.so.1 (0x40353000) libz.so.1 => /usr/lib/libz.so.1 (0x403e2000) libpng.so.2 => /usr/lib/libpng.so.2 (0x403f0000) libmysqlclient.so.11 => /usr/lib/libmysqlclient.so.11 (0x40411000) libming.so => /usr/lib/libming.so (0x40449000) libm.so.6 => /lib/libm.so.6 (0x40487000) libfreetype.so.6 => /usr/lib/libfreetype.so.6 (0x404a8000) libjpeg.so.62 => /usr/lib/libjpeg.so.62 (0x404e7000) libcrypt.so.1 => /lib/libcrypt.so.1 (0x40505000) libssl.so.2 => /lib/libssl.so.2 (0x40532000) libcrypto.so.2 => /lib/libcrypto.so.2 (0x40560000) libresolv.so.2 => /lib/libresolv.so.2 (0x40624000) libdl.so.2 => /lib/libdl.so.2 (0x40634000) libnsl.so.1 => /lib/libnsl.so.1 (0x40637000) libc.so.6 => /lib/libc.so.6 (0x4064b000) /lib/ld-linux.so.2 => /lib/ld-linux.so.2 (0x80000000) °Ô´Ù°¡, ÀÌ ¶óÀ̺귯¸®µé ¿Ü¿¡µµ ¸ðµâ¿¡ Á¤ÀûÀ¸·Î ¸µÅ©µÈ ¶óÀ̺귯¸®°¡ ÀÖ´Ù¸é ÀÌ°Í ¿ª½Ã È®ÀÎÇØ º¸¾Æ¾ß ÇÕ´Ï´Ù. °¢ ¸ðµâÀÇ °³º° ½Éº¼À» º¸±â À§Çؼ´Â nm(1)À» »ç¿ëÇÒ ¼ö ÀÖ½À´Ï´Ù.
5. Library List ¶ÀÌ ¸®½ºÆ®¿¡ Ãß°¡ÇÏ¿©¾ß Çϰųª ¼öÁ¤ÇØ¾ß ÇÒ »çÇ×ÀÌ ÀÖ´Ù¸é dev@httpd.apache.org ·Î ¿¬¶ôÀ» ÁֽʽÿÀ.
|