macOSçšPVS-Studio
macOSçšã®ã¢ãã©ã€ã¶ãŒããŒãžã§ã³ã®ãªãªãŒã¹ã«ãããPVS-Studioã¯Cããã³C ++ã®ã¯ãã¹ãã©ãããã©ãŒã éçã³ãŒãã¢ãã©ã€ã¶ãŒãšå®å šã«åŒã°ããããã«ãªããŸããã
æåã¯ãWindowså°çšã®ããŒãžã§ã³ããããŸããã çŽ2幎åãç§ãã¡ã®ããŒã ã¯LinuxããµããŒãããŠããŸããããLinuxã§PVS-Studioãäœæããæ¹æ³ ãã ãŸããç§ãã¡ã®ããã°ã®æ³šææ·±ãèªè ã¯ãFreeBSDã«ãŒãã«ã®ãã§ãã¯ã«é¢ããèšäºïŒ 第1èšäº ã 第2èšäº ïŒãæãåºããŠãã ãã ã ãã®åŸãã¢ãã©ã€ã¶ãŒã¯PC-BSDããã³TrueOSã§å®è¡ããããã«æ§ç¯ãããŸããã ãããŠæåŸã«ãmacOSã«å°éããŸããïŒ
ã¯ãã¹ãã©ãããã©ãŒã 補åã®éçºã¯ç°¡åã§ããïŒ
ãã®åé¡ã«ã¯çµæžçããã³æè¡çãªèŠçŽ ããããŸãã
çµæžçãªèŠ³ç¹ãããã¢ãã©ã€ã¶ãŒãã¯ãã¹ãã©ãããã©ãŒã ã«ããããšã¯æ£ãã決æã§ããã ãœãããŠã§ã¢éçºã¯é·ãéãã®æ¹åã«åãã£ãŠããããã®ãããªãããžã§ã¯ãã®éçºè åãã®ããŒã«ã¯é©åãªã¯ãã§ãã ãã ããäœãæçšãªãã®ããããšããŠããããã«å§ãã䟡å€ããããšããæå³ã§ã¯ãããŸããã æåã¯ãåžžã«æ°ããæ¹åã«äœããå®çŸããã®ã«ååãªåãããããšã確èªããããããµããŒãããŸãã
æè¡çãªé¢ããèŠããšããããžã§ã¯ããããã«ã¯ãã¹ãã©ãããã©ãŒã ãšããŠèããããªãéããæåããå°é£ã§ãã ã¢ãã©ã€ã¶ãŒãLinuxã·ã¹ãã ã«é©å¿ãããã®ã«æ°ã¶æãè²»ãããŸããã æ°ãããã©ãããã©ãŒã çšã«ãããžã§ã¯ããã³ã³ãã€ã«ããã®ã«å€ãã®æéã¯ããããŸããã§ãããã°ã©ãã£ã«ã«ã€ã³ã¿ãŒãã§ã€ã¹ããªããã³ãŒãã¯å®éã«ã¯ã·ã¹ãã APIã®äœ¿çšã«é¢é£ä»ããããŠããŸããã ã»ãšãã©ã®æéã¯ãã¢ãã©ã€ã¶ãŒãæ°ããã³ã³ãã€ã©ãŒã«é©åãããåæã®å質ãåäžãããããã«è²»ããããŸããã èšãæããã°ãå€ãã®åªåã«ã¯èª€æ€ç¥ã®é²æ¢ãå¿ èŠã§ãã
macOSéçºã¯ã©ãã§ããïŒ
ãã®æç¹ã§ãCMakeçšã®ãããžã§ã¯ãã¢ãã©ã€ã¶ãŒãã¡ã€ã«ãæ¢ã«ãããããŸããŸãªãªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã«ç°¡åã«é©å¿ã§ããŸãã ããŸããŸãªã¿ã€ãã®ãã¹ãã·ã¹ãã ãã¯ãã¹ãã©ãããã©ãŒã ã§ããã ããã¯ãã¹ãŠãmacOSã§éåžžã«è¿ éã«èµ·åããã®ã«åœ¹ç«ã¡ãŸããã
macOSã®ã¢ãã©ã€ã¶ãŒéçºæ©èœã¯ãApple LLVM Compilerã§ããã ã¢ãã©ã€ã¶ãŒã¯GCCã䜿çšããŠæ§ç¯ãããå®å šã«æ©èœããŸããããä»åŸãã¢ãã©ã€ã¶ãŒãšãŠãŒã¶ãŒã®ã³ã³ãã¥ãŒã¿ãŒã®äºææ§ã«åœ±é¿ãäžããå¯èœæ§ããããŸãã æœåšçãªãŠãŒã¶ãŒã«åé¡ãçããããªãããã«ãXcodeã«ä»å±ããŠãããã®ã³ã³ãã€ã©ã䜿çšããé åžãã«ãããµããŒãããããšã«ããŸããã
C ++ã®éçºã¯ãã¯ãã¹ãã©ãããã©ãŒã ãããžã§ã¯ãã®äœæãšéçºã«å€§ãã«åœ¹ç«ã¡ãŸãããããŸããŸãªã³ã³ãã€ã©ããã®ãããªæ©èœãéåžžã«äžåçã«è¿œå ãããããæ¡ä»¶ã³ã³ãã€ã«ã¯ããã€ãã®å Žæã§ç©æ¥µçã«äœ¿çšãããŠããŸãã
äžè¬çã«ããã¹ãŠãç°¡åãã€ã¹ã ãŒãºã«é²ã¿ãŸããã 以åãšåæ§ã«ãã»ãšãã©ã®æéã¯äŸå€ã®ç¢ºå®ããµã€ãã®å€æŽããã¹ãããã®ä»ã®é¢é£ããåé¡ã«è²»ããããŸããã PVS-Studio for macOSã§ãã¹ããããæåã®ãããžã§ã¯ããšããŠã XNU Kernelã玹ä»ããŸãã
é åž
ãã¡ãããmacOSçšPVS-StudioãããŠã³ããŒãããŠã€ã³ã¹ããŒã«ããæ¹æ³ãç解ã§ããŸã ã
XNUã«ãŒãã«
ãã®ã·ã¹ãã ã®ã«ãŒãã«ããã§ãã¯ããªãå ŽåãmacVSçšPVS-Studioã®æ©èœã®ãã¢ãéå§ããå ŽæïŒ ãããã£ãŠãã¢ãã©ã€ã¶ãŒã®æ°ããããŒãžã§ã³ã䜿çšããŠãã¹ããããæåã®ãããžã§ã¯ãã¯XNUã«ãŒãã«ã§ããã
XNUã¯ãAppleãéçºããOS Xãã¡ããªãŒã®OSïŒmacOSãiOSãtvOSãwatchOSïŒã§äœ¿çšãããã³ã³ãã¥ãŒã¿ãŒãªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã®äžæ žã§ãã 詳现
ã«ãŒãã«ã¯Cããã³C ++ã§èšè¿°ãããŠãããšèããããŠããŸãããå®éã¯Cã§ãã1302* .cãã¡ã€ã«ãš97 * .cppãã¡ã€ã«ã®ã¿ãã«ãŠã³ãããŸããã ã³ãŒãããŒã¹ã®ãµã€ãºã¯1929 KLOCã§ãã ããã¯æ¯èŒçå°ããªãããžã§ã¯ãã§ããããšãããããŸããã æ¯èŒã®ããã«ãChromiumãããžã§ã¯ãã®ã³ãŒãããŒã¹ã¯15å倧ããã30 MLOCãå«ãŸããŠããŸãã
ãœãŒã¹ã³ãŒãã¯ãGitHub Webãµã€ãã®ãã©ãŒxnuããç°¡åã«ããŠã³ããŒãã§ããŸãã
æ€èšŒçµæ
XNU Kernelãããžã§ã¯ãã¯æ¯èŒçå°ããªãã®ã§ãããã¢ãã©ã€ã¶ãŒã®èŠåã ãã調ã¹ãããšã¯ãå€ãã®æéãããã倧ããªã¿ã¹ã¯ã§ãã ã¢ãã©ã€ã¶ãŒãäºåã«æ§æããªãã£ããããèŠåãšèª€å ±ã®èª¿æ»ãè€éã«ãªããŸããã ç§ã®æèŠã§ã¯ãããã«èŠåãå®è¡ããèå³ã®ããã³ãŒãã®æçãæžããŸããã ããã¯ãèšäºãæžãã®ã«ååã§ãããããããµã€ãºããã£ããããŠããŸãã PVS-Studioã¢ãã©ã€ã¶ãŒã¯ãå€æ°ã®èå³æ·±ããšã©ãŒãç°¡åã«æ€åºããŸãã
XNUã«ãŒãã«éçºè ãžã®æ³šæ ã ã§ããã ãå€ãã®ãšã©ãŒãèŠã€ããäœæ¥ã¯ãããŸããã§ããã ãããã£ãŠããã®èšäºãèªãã§ä¿®æ£ããããšã¯ã§ããŸããã ãŸããã¢ã©ãŒããããã²ãŒãããæ¹æ³ããªããããããã¯äžäŸ¿ã§ãã PVS-Studioãçæã§ãã圢åŒã®1ã€ãããšãã°ãããã²ãŒãæ©èœãåããHTMLã¬ããŒãïŒClangãçæã§ãããã®ã«äŒŒãŠããŸãïŒã䜿çšããæ¹ãã¯ããã«åªããŠãããšç¢ºä¿¡ããŠããŸãã 第äºã«ãã¬ããŒããè¡šé¢çã«ç 究ãããšããã ãã®çç±ã§ãå€ãã®ééããéããŸããã éçºè ã¯ãPVS-Studioã䜿çšããŠããããžã§ã¯ãã®ãã培åºçãªåæãç¬èªã«å®è¡ããããšããå§ãããŸãã
å ã»ã©èšã£ãããã«ã誀æ€ç¥ã¯ç§ã劚害ããŸããããå®éã«ã¯åé¡ã§ã¯ãããŸããã ã¢ãã©ã€ã¶ãŒãæ§æããå Žåã誀æ€ç¥ã®æ°ã10-15ïŒ æžããããšãã§ããŸãã åæããã»ã¹ã®ã»ããã¢ãããšåèµ·åã«ãæéããããããããã®æé ãã¹ãããããŸãããèšäºãªãã§èšäºã®ãšã©ãŒãåéããã®ã¯ç°¡åã§ãã åæãæ éã«å®è¡ããããšãèšç»ããŠããå Žåã¯ããã¡ãããæéããããŠæ§æããå¿ èŠããããŸãã
倧éšåã®èª€æ€ç¥ã¯ããã¯ããšååã«ããŒã¯ãããŠããªãé¢æ°ãåå ã§çºçããŸãã ããšãã°ãXNUã«ãŒãã«ã§ã¯ããããã®ã»ãšãã©ã¯ãããã¯æ©èœã®äœ¿çšã«é¢é£ä»ããããŠããŸãã
ãããããã®é¢æ°ã®å®£èšæ¹æ³ã§ãã
extern void panic(const char *string, ...) __attribute__((__format__ (__printf__, 1, 2)));
ãã®é¢æ°ã«ã¯æ³šéãä»ããããŠãããããå ¥ååŒæ°ã¯printfé¢æ°ã®åŒæ°ãšã®é¡æšã«ãã£ãŠè§£éãããŸãã ããã«ãããã³ã³ãã€ã©ãŒããã³ã¢ãã©ã€ã¶ãŒã¯ã誀ã£ãã¹ããªã³ã°åœ¢åŒã®ãšã©ãŒãèŠã€ããããšãã§ããŸãã ãã ããé¢æ°ã¯å¶åŸ¡ãè¿ããªããšããŒã¯ãããŠããŸããã ãã®çµæã次ã®ã³ãŒãã¯èª€æ€ç¥ã«ã€ãªãããŸãã
if (!ptr) panic("zzzzzz"); memcpy(ptr, src, n);
ããã§ãã¢ãã©ã€ã¶ãŒã¯ãnullãã€ã³ã¿ãŒãéåç §ã§ãããšããèŠåãåºããŸãã 圌ã®èŠ³ç¹ããã ãããã¯é¢æ°ãåŒã³åºããåŸã memcpyé¢æ°ãåŒã³åºãããŸãã
ãã®ãããªèª€æ€ç¥ãåé¿ããã«ã¯ã __attribute __ïŒïŒnoreturnïŒïŒãè¿œå ããŠé¢æ°ã®æ³šéãå€æŽããå¿ èŠããããŸãã
extern __attribute__((noreturn)) void panic(const char *string, ...) __attribute__((__format__ (__printf__, 1, 2)));
ããã§ãXNU Kernelã³ãŒãã§äœã«èå³ãæã£ãããèŠãŠã¿ãŸãããã åèšã§ã64åã®ãšã©ãŒãæžãããã®çŸããæ°ã«ãã ããããšã«ããŸããã å€ãã®äººã¯ãã®åé¡ã«ç²ŸéããŠããããã Common Weakness Enumerationã«åŸã£ãŠæ¬ é¥ãã°ã«ãŒãåããç¹å®ã®ç« ã§èª¬æãããŠãããšã©ãŒãç解ãããããªããŸãã
CWE-570 / CWE-571ïŒåŒã¯åžžã«False / Trueã§ã
éåžžã«å€æ§ãªãšã©ãŒã¯ã CWE-570 / CWE-571ã«ã€ãªããå¯èœæ§ããããŸãã æ¡ä»¶ãŸãã¯æ¡ä»¶ã®äžéšãåžžã«false / trueã§ããç¶æ³ã XNU Kernelãããžã§ã¯ãã®å Žåããããã®ãšã©ãŒã¯ãã¹ãŠãç§ã®æèŠã§ã¯ãã¿ã€ããã¹ã«é¢é£ããŠããŸãã PVS-Studioã¯éåžžãã¿ã€ããã¹ãéåžžã«ããèå¥ããŸãã
ãã©ã°ã¡ã³ãN1
int key_parse( struct mbuf *m, struct socket *so) { .... if ((m->m_flags & M_PKTHDR) == 0 || m->m_pkthdr.len != m->m_pkthdr.len) { ipseclog((LOG_DEBUG, "key_parse: invalid message length.\n")); PFKEY_STAT_INCREMENT(pfkeystat.out_invlen); error = EINVAL; goto senderror; } .... }
PVS-Studioã®èŠåïŒV501 CWE-570 'ïŒ='æŒç®åã®å·ŠåŽãšå³åŽã«ã¯ãåäžã®éšååŒ 'm-> M_dat.MH.MH_pkthdr.len'ããããŸãã key.c 9442
ã¿ã€ããã¹ã«ãããã¯ã©ã¹ã®ã¡ã³ããŒã¯ããèªèº«ãšæ¯èŒãããŸãïŒ
m->m_pkthdr.len != m->m_pkthdr.len
æ¡ä»¶ã®äžéšã¯åžžã«falseã§ããããã®çµæãã¡ãã»ãŒãžã®é·ãã誀ã£ãŠãã§ãã¯ãããŸãã ããã°ã©ã ã誀ã£ãããŒã¿ãåŠçãç¶ããããšãå€æããŸããã æããããã¯æãããããšã§ã¯ãããŸããããå€ãã®è匱æ§ã¯ãç¹å®ã®å ¥åããŒã¿ãæªãã§ãã¯ã§ããããååãªæ¹æ³ã§æ€èšŒãããªãã£ãããšãåå ã§ãã ãããã£ãŠãã³ãŒãå ã®ãã®å Žæã¯ãéçºè ã®æ³šç®ã«å€ããŸãã
ãã©ã°ã¡ã³ãN2ãN3
#define VM_PURGABLE_STATE_MASK 3 kern_return_t memory_entry_purgeable_control_internal(...., int *state) { .... if ((control == VM_PURGABLE_SET_STATE || control == VM_PURGABLE_SET_STATE_FROM_KERNEL) && (((*state & ~(VM_PURGABLE_ALL_MASKS)) != 0) || ((*state & VM_PURGABLE_STATE_MASK) > VM_PURGABLE_STATE_MASK))) return(KERN_INVALID_ARGUMENT); .... }
PVS-StudioèŠåïŒV560 CWE-570æ¡ä»¶åŒã®äžéšãåžžã«falseã§ãïŒïŒïŒ* stateïŒ3ïŒ> 3ïŒã vm_user.c 3415
åŒã®ãã®éšåãããã«è©³ããèããŠã¿ãŸãããã
(*state & VM_PURGABLE_STATE_MASK) > VM_PURGABLE_STATE_MASK
ãã¯ãå€ã眮æãããšã次ã®ããã«ãªããŸãïŒ
(*state & 3) > 3
ãããåäœã®ANDæŒç®ã®çµæã¯ãå€0ã1ããŸãã¯2ã®ã¿ã«ãªããŸãã0ã1ããŸãã¯2ã3ãã倧ãããã©ããããã§ãã¯ããããšã¯æå³ããããŸããã
åã®ã±ãŒã¹ãšåæ§ã«ãç¹å®ã®ã¹ããŒã¿ã¹ã誀ã£ãŠãã§ãã¯ãããããã誀ã£ãïŒèª€ã£ãïŒããŒã¿ãåŠçãããå¯èœæ§ããããŸãã
vm_map.cãã¡ã€ã«ã«ããŸã£ããåããšã©ãŒãèŠã€ãããŸãã ã©ããããã³ãŒãã®äžéšã¯Copy-Pasteã䜿çšããŠæžãããããã§ãã èŠåïŒV560 CWE-570æ¡ä»¶åŒã®äžéšã¯åžžã«falseã§ãïŒïŒïŒ* stateïŒ3ïŒ> 3ïŒã vm_map.c 15809
ãã©ã°ã¡ã³ãN4
void pat_init(void) { boolean_t istate; uint64_t pat; if (!(cpuid_features() & CPUID_FEATURE_PAT)) return; istate = ml_set_interrupts_enabled(FALSE); pat = rdmsr64(MSR_IA32_CR_PAT); DBG("CPU%d PAT: was 0x%016llx\n", get_cpu_number(), pat); /* Change PA6 attribute field to WC if required */ if ((pat & ~(0x0FULL << 48)) != (0x01ULL << 48)) { mtrr_update_action(CACHE_CONTROL_PAT); } ml_set_interrupts_enabled(istate); }
PVS-StudioèŠåïŒV547 CWE-571åŒã¯åžžã«çã§ãã mtrr.c 692
ã¿ã€ããã¹ãäŸµå ¥ããå¯èœæ§ãé«ãç¡æå³ãªãã§ãã¯ãèŠãŠã¿ãŸãããã
(pat & ~(0x0FULL << 48)) != (0x01ULL << 48)
ããã€ãã®åŒãèšç®ããŸãïŒ
- ãïŒ0x0FULL << 48ïŒ= 0xFFF0FFFFFFFFFFFF
- ïŒ0x01ULL << 48ïŒ= 0x0001000000000000
åŒïŒpatïŒ[0xFFF0FFFFFFFFFFFFFF]ïŒã®å€ã¯0x0001000000000000ã«ãªããŸããã æ¡ä»¶ã¯åžžã«çã§ãã ãã®çµæã mtrr_update_actioné¢æ°ãåžžã«åŒã³åºãããŸãã
ãã©ã°ã¡ã³ãN5
ä»ãç§ã®æèŠã§ã¯ãéåžžã«çŸããã¿ã€ããã¹ããããŸãïŒ ==ã®ä»£ããã«= ãæžããŸããã
typedef enum { CMODE_WK = 0, CMODE_LZ4 = 1, CMODE_HYB = 2, VM_COMPRESSOR_DEFAULT_CODEC = 3, CMODE_INVALID = 4 } vm_compressor_mode_t; void vm_compressor_algorithm_init(void) { .... assertf(((new_codec == VM_COMPRESSOR_DEFAULT_CODEC) || (new_codec == CMODE_WK) || (new_codec == CMODE_LZ4) || (new_codec = CMODE_HYB)), "Invalid VM compression codec: %u", new_codec); .... }
PVS-StudioèŠåïŒV768 CWE-571åŒãnew_codec = CMODE_HYBãã¯åæåã§ãã ããŒã«åã®åŒãšããŠäœ¿çšãããã®ã¯å¥åŠã§ãã vm_compressor_algorithms.c 419
æ¡ä»¶ããã§ãã¯ããããã»ã¹ã§ã¯ãå€æ°new_codecã«å€2 ãå²ãåœãŠãããŸãããã®çµæãæ¡ä»¶ã¯åžžã«trueã«ãªããã¢ãµãŒããã¯ãã¯å®éã«ã¯äœããã§ãã¯ããŸããã
ééãã¯ç¡å®³ã§ãã ãŸããã¢ãµãŒããã¯ãã¯äœãããã§ãã¯ããŸããã§ãã-ããã¯éèŠã§ã¯ãããŸããã ãã ããããã«å ããŠããããã°ããŒãžã§ã³ãæ£ããæ©èœããŸããã çµå±ã new_codecå€æ°ã®å€ã¯æãªãããå¿ èŠãªã³ãŒããã¯ã¯äœ¿çšãããŸããã
ãã©ã°ã¡ã³ãN6ãN7
void pbuf_copy_back(pbuf_t *pbuf, int off, int len, void *src) { VERIFY(off >= 0); VERIFY(len >= 0); VERIFY((u_int)(off + len) <= pbuf->pb_packet_len); if (pbuf->pb_type == PBUF_TYPE_MBUF) m_copyback(pbuf->pb_mbuf, off, len, src); else if (pbuf->pb_type == PBUF_TYPE_MBUF) { if (len) memcpy(&((uint8_t *)pbuf->pb_data)[off], src, len); } else panic("%s: bad pb_type: %d", __func__, pbuf->pb_type); }
PVS-StudioèŠåïŒV517 CWE-570ãifïŒAïŒ{...} else ifïŒAïŒ{...}ããã¿ãŒã³ã®äœ¿çšãæ€åºãããŸããã è«çãšã©ãŒãååšããå¯èœæ§ããããŸãã è¡ã確èªããŠãã ããïŒ340ã343ãpf_pbuf.c 340
æ確ã«ããããã«ãæ¬è³ªã匷調ããŸãã
if (A) foo(); else if (A) Unreachable_code; else panic();
æ¡ä»¶Aãçã®å Žåãæåã®ifã¹ããŒãã¡ã³ãã®æ¬æã¯çã§ãã ããã§ãªãå Žåã¯ãå確èªããŠãæå³ããªãã ãããã¯æ©èœãããã«åŒã³åºãããŸãã éåžžãã³ãŒãã®äžéšã¯éæã§ããŸããã
ããã§ã¯ãããžãã¯ã®äœããã®çš®é¡ã®ãšã©ãŒããŸãã¯ããããã®æ¡ä»¶ã®ã¿ã€ããã¹ããããŸãã
åããã¡ã€ã«å ã®pbuf_copy_dataé¢æ°ã¯ã ã»ãšãã©ã®å ŽåãCopy-Pasteã䜿çšããŠèšè¿°ãããŠãããåããšã©ãŒãå«ãŸããŠããŸãã èŠåïŒV517 CWE-570ãifïŒAïŒ{...} else ifïŒAïŒ{...}ããã¿ãŒã³ã®äœ¿çšãæ€åºãããŸããã è«çãšã©ãŒãååšããå¯èœæ§ããããŸãã è¡ã確èªããŠãã ããïŒ358ã361ãpf_pbuf.c 358
CWE-670ïŒåžžã«æ£ãããªãå¶åŸ¡ãããŒã®å®è£
CWE-670ã®æ¬ é¥ã¯ãããããã³ãŒãå ã§ãããã°ã©ããæå³ãããšããã«äœããæ©èœããªãããšã瀺åããŠããŸãã
ãã©ã°ã¡ã³ãN8ãN9ãN10
static void in_ifaddr_free(struct ifaddr *ifa) { IFA_LOCK_ASSERT_HELD(ifa); if (ifa->ifa_refcnt != 0) { panic("%s: ifa %p bad ref cnt", __func__, ifa); /* NOTREACHED */ } if (!(ifa->ifa_debug & IFD_ALLOC)) { panic("%s: ifa %p cannot be freed", __func__, ifa); /* NOTREACHED */ } if (ifa->ifa_debug & IFD_DEBUG) { .... }
PVS-StudioèŠåïŒV646 CWE-670ã¢ããªã±ãŒã·ã§ã³ã®ããžãã¯ã®æ€æ»ãæ€èšããŠãã ããã ãelseãããŒã¯ãŒããæ¬ èœããŠããå¯èœæ§ããããŸãã in.c 2010
ããããããã®ã³ãŒãã«ã¯ãšã©ãŒã¯ãããŸããã ãã ãããã®å Žæã¯éåžžã«çãããããã§ãã
} if (!(ifa->ifa_debug & IFD_ALLOC)) {
äŸå€ã¯ãæç« ãåãå ¥ããããªãããšã§ãã æ°ããè¡ããã®å Žåã¯ãæžã蟌ã¿ãéå§ããæ¹ãè«ççã§ãã ã³ãŒãäœæè ã¯ãã®å Žæã確èªããå¿ èŠããããŸãã ããããelseããŒã¯ãŒããããã«ãããŸãããã³ãŒãã¯æ¬¡ã®ããã«ãªããŸãã
} else if (!(ifa->ifa_debug & IFD_ALLOC)) {
ãŸãã¯ãæ¹è¡ãè¿œå ããã ãã§ããã®ã³ãŒããã¢ãã©ã€ã¶ãŒãŸãã¯ãã®ã³ãŒãã«é¢ä¿ããååã«ãã£ãŠæ··åãããªãããã«ããããšãã§ããŸãã
åæ§ã®äžå¯©ãªå Žæã¯ããã«ãããŸãïŒ
- V646 CWE-670ã¢ããªã±ãŒã·ã§ã³ã®ããžãã¯ã®æ€æ»ãæ€èšããŠãã ããã ãelseãããŒã¯ãŒããæ¬ èœããŠããå¯èœæ§ããããŸãã kern_malloc.c 836
- V646 CWE-670ã¢ããªã±ãŒã·ã§ã³ã®ããžãã¯ã®æ€æ»ãæ€èšããŠãã ããã ãelseãããŒã¯ãŒããæ¬ èœããŠããå¯èœæ§ããããŸãã ipc_kmsg.c 4229
ãã©ã°ã¡ã³ãN11ãNââ12ãN13ãN14
int dup2(proc_t p, struct dup2_args *uap, int32_t *retval) { .... while ((fdp->fd_ofileflags[new] & UF_RESERVED) == UF_RESERVED) { fp_drop(p, old, fp, 1); procfdtbl_waitfd(p, new); #if DIAGNOSTIC proc_fdlock_assert(p, LCK_MTX_ASSERT_OWNED); #endif goto startover; } .... startover: .... }
PVS-StudioèŠåïŒV612 CWE-670ã«ãŒãå ã®ç¡æ¡ä»¶ã®ãgotoãã kern_descrip.c 628
ããã¯éåžžã«å¥åŠãªã³ãŒãã§ãã whileã¹ããŒãã¡ã³ãã®æ¬äœã¯gotoã¹ããŒãã¡ã³ãã§çµäºããããšã«æ³šæããŠãã ãã ã ãã®å Žåãã«ãŒãæã®ã©ãã§ãcontinueã¹ããŒãã¡ã³ãã¯äœ¿çšãããŸããã ããã¯ããµã€ã¯ã«ã®æ¬äœãè€æ°åå®è¡ãããªãããšãæå³ããŸãã
ããã§ãã«ãŒããè€æ°åå®è¡ããªãã®ã«ããªãã«ãŒããäœæããå¿ èŠããã£ãã®ã§ããïŒ ifã¹ããŒãã¡ã³ãã䜿çšããæ¹ãè¯ãã§ãããããããŠããã¯åé¡ãæèµ·ããŸããã ããã¯ééãã§ãããã«ãŒãå ã§äœããééã£ãŠèšè¿°ãããŠãããšæããŸãã ããšãã°ã gotoã¹ããŒãã¡ã³ãã®åã«æ¡ä»¶ãæ¬ èœããŠããå¯èœæ§ããããŸãã
åæ§ã®ãã¯ã³ã¿ã€ã ããµã€ã¯ã«ãããã«3åçºçããŸãã
- V612 CWE-670ã«ãŒãå ã®ç¡æ¡ä»¶ã®ãgotoãã tty.c 1084
- V612 CWE-670ã«ãŒãå ã®ç¡æ¡ä»¶ã®ãgotoãã vm_purgeable.c 842
- V612 CWE-670ã«ãŒãå ã®ç¡æ¡ä»¶ã®ãæ»ããã kern_credential.c 930
ãã«ãã€ã³ã¿ãŒã®éåç §ïŒCWE-476ãCWE-628ãCWE-690
nullãã€ã³ã¿ãŒã®éåç §ãçºçããå¯èœæ§ãããããŸããŸãªçç±ããããPVS-Studioã¢ãã©ã€ã¶ãŒã¯ç¶æ³ã«å¿ããŠç°ãªãCWE-IDãå²ãåœãŠãå ŽåããããŸãã
- CWE-476 ïŒNULLãã€ã³ã¿ãŒéåç §
- CWE-628 ïŒåŒæ°ãæ£ããæå®ãããŠããªãé¢æ°åŒã³åºã
- CWE-690 ïŒNULLãã€ã³ã¿ãŒéåç §ãžã®æªãã§ãã¯ã®æ»ãå€
èšäºãæžããšãããã®ã¿ã€ãã®ãã¹ãŠã®ãšã©ãŒã1ã€ã®ã»ã¯ã·ã§ã³ã«éããã®ã劥åœã§ãããšèããŸããã
ãã©ã°ã¡ã³ãN15
è€éã§åªããæ©èœããå§ããŸãã ãŸããé¢æ°netagent_send_error_responseãæ€èšããŸãããã®é¢æ°ã§ã¯ã ã»ãã·ã§ã³åŒæ°ã§æž¡ããããã€ã³ã¿ãŒãéåç §ãããŸãã
static int netagent_send_error_response( struct netagent_session *session, u_int8_t message_type, u_int32_t message_id, u_int32_t error_code) { int error = 0; u_int8_t *response = NULL; size_t response_size = sizeof(struct netagent_message_header); MALLOC(response, u_int8_t *, response_size, M_NETAGENT, M_WAITOK); if (response == NULL) { return (ENOMEM); } (void)netagent_buffer_write_message_header(.....); if ((error = netagent_send_ctl_data(session->control_unit, (u_int8_t *)response, response_size))) { NETAGENTLOG0(LOG_ERR, "Failed to send response"); } FREE(response, M_NETAGENT); return (error); }
ã»ãã·ã§ã³ãã€ã³ã¿ãŒã¯ãäºåã®æ€èšŒãªãã«ã session-> control_unitåŒã§éæ¥åç §ãããããšã«æ³šæããŠãã ããã NULLãã€ã³ã¿ãŒãéåç §ããããã©ããã¯ããã®é¢æ°ã«æž¡ãããå®éã®åŒæ°ã«ãã£ãŠç°ãªããŸãã
ããã§ãäžèšã®netagent_send_error_responseé¢æ°ãnetagent_handle_unregister_messageé¢æ°ã§ã©ã®ããã«äœ¿çšãããããèŠãŠã¿ãŸãããã
static void netagent_handle_unregister_message( struct netagent_session *session, ....) #pragma unused(payload_length, packet, offset) u_int32_t response_error = NETAGENT_MESSAGE_ERROR_INTERNAL; if (session == NULL) { NETAGENTLOG0(LOG_ERR, "Failed to find session"); response_error = NETAGENT_MESSAGE_ERROR_INTERNAL; goto fail; } netagent_unregister_session_wrapper(session); netagent_send_success_response(session, .....); return; fail: netagent_send_error_response( session, NETAGENT_MESSAGE_TYPE_UNREGISTER, message_id, response_error); }
PVS-StudioèŠåïŒV522 CWE-628ãã«ãã€ã³ã¿ãŒãã»ãã·ã§ã³ãã®éåç §ãè¡ãããå ŽåããããŸãã ãã«ãã€ã³ã¿ãŒã¯ 'netagent_send_error_response'é¢æ°ã«æž¡ãããŸãã æåã®åŒæ°ã調ã¹ãŸãã è¡ã確èªããŠãã ããïŒ427ã972ãnetwork_agent.c 427
ããã§ã¯ãPVS-Studioã«å®è£ ãããããŒã¿ãããŒåæãçŸããŸãã ã¢ãã©ã€ã¶ãŒã¯ã ã»ãã·ã§ã³ãã€ã³ã¿ãŒãNULLã§ããå Žåããã°ã«äœããã®æ å ±ãæžã蟌ãŸãããã®åŸã 倱æã©ãã«ãžã®é·ç§»ãçºçããããšã芳å¯ããŸãã
以äžã¯ã netagent_send_error_responseé¢æ°ã®åŒã³åºãã§ãã
fail: netagent_send_error_response( session, NETAGENT_MESSAGE_TYPE_UNREGISTER, message_id, response_error);
NULLã§ããäžéãªã»ãã·ã§ã³ãã€ã³ã¿ãŒã¯ãå®éã®åŒæ°ãšããŠé¢æ°ã«æž¡ãããããšã«æ³šæããŠãã ããã
ç¥ã£ãŠããããã«ã netagent_send_error_responseé¢æ°ã§ã¯ããã®å Žåã®ä¿è·ã¯ãªããnullãã€ã³ã¿ãŒãéåç §ãããŸãã
ãã©ã°ã¡ã³ãN16
次ã®ç¶æ³ã¯åã®ç¶æ³ãšäŒŒãŠããŸãã é¢æ°ã³ãŒãã¯çããªããŸããããã£ãããšè©³çŽ°ã«å¯ŸåŠããå¿ èŠããããŸãã
void * pf_lazy_makewritable(struct pf_pdesc *pd, pbuf_t *pbuf, int len) { void *p; if (pd->lmw < 0) return (NULL); VERIFY(pbuf == pd->mp); p = pbuf->pb_data; if (len > pd->lmw) { .... }
æåã«NULLããã§ãã¯ããã«pbufãã€ã³ã¿ãŒãéåç §ãããããšã«æ³šæããŠãã ããã ã³ãŒãã«ã¯ãVERIFYïŒpbuf == pd-> mpïŒããšãããã§ãã¯ããããŸãã ãã ãã pd-> mpã¯NULLã«ãªãå Žåããããããæ€èšŒã¯NULLã«å¯Ÿããä¿è·ãšã¯èŠãªãããŸããã
ã泚æ ç§ã¯XNUã«ãŒãã«ã³ãŒãã«å®å šã«äžæ £ãã§ãããééã£ãŠããå¯èœæ§ãããããšã«æ³šæããŠãã ããã ããããã pd-> mpã¯NULLå€ãæ ŒçŽããããšã¯ãããŸããã ããããç§ã®æšè«ã¯ãã¹ãŠééã£ãŠãããããã«ééãã¯ãããŸããã ããã§ãããã®ãããªã³ãŒãã¯ããäžåºŠç¢ºèªããæ¹ãè¯ãã§ãããã
ç¶ããŠãèæ ®ãããpf_lazy_makewritableé¢æ°ãã©ã®ããã«äœ¿çšãããããèŠãŠã¿ãŸããã ã
static int pf_test_state_icmp(....) { .... if (pf_lazy_makewritable(pd, NULL, off + sizeof (struct icmp6_hdr)) == NULL) return (PF_DROP); .... }
PVS-StudioèŠåïŒV522 CWE-628ãã«ãã€ã³ã¿ãŒãpbufãã®éåç §ãè¡ãããå ŽåããããŸãã NULLãã€ã³ã¿ãŒã¯ãpf_lazy_makewritableãé¢æ°ã«æž¡ãããŸãã 2çªç®ã®åŒæ°ã調ã¹ãŸãã è¡ã確èªïŒ349ã7460ãpf.c 349
2çªç®ã®å®åŒæ°ãšããŠã pf_lazy_makewritableé¢æ°ã«NULLãæž¡ãããŸãã ããã¯éåžžã«å¥åŠã§ãã
ããã°ã©ããŒããããã°ã©ã ããVERIFYïŒpbuf == pd-> mpïŒãããã«ãã€ã³ã¿ãŒããä¿è·ãããšèããŠãããšããŸãã ãã®åŸãçåãçããŸãããªããã®ãããªã³ãŒããæžããã®ã§ããïŒ æããã«ç¡å¹ãªåŒæ°ãæž¡ããŠé¢æ°ãåŒã³åºãã®ã¯ãªãã§ããïŒ
ãããã£ãŠãå®éã«ã¯ã pf_lazy_makewritableé¢æ°ã¯nullãã€ã³ã¿ãŒãåãå ¥ããäœããã®æ¹æ³ã§ãã®ã±ãŒã¹ãç¹å¥ãªæ¹æ³ã§åŠçã§ããã¯ãã§ãããããã§ã¯ãããŸããã ãã®ã³ãŒãã¯ããã°ã©ããŒã«ããæã培åºçãªæ€èšŒã«å€ããPVS-Studioã¢ãã©ã€ã¶ãŒã¯ééããªãæ£ããã®ã§ã泚æãæã£ãŠããŸãã
ãã©ã°ã¡ã³ãN17
å°ããªã©ãã¯ã¹ã§ããŸããç°¡åãªã±ãŒã¹ãèããŠã¿ãŸãããã
typedef struct vnode * vnode_t; int cache_lookup_path(...., vnode_t dp, ....) { .... if (dp && (dp->v_flag & VISHARDLINK)) { break; } if ((dp->v_flag & VROOT) || dp == ndp->ni_rootdir || dp->v_parent == NULLVP) break; .... }
PVS-StudioèŠåïŒV522 CWE-690æœåšçãªãã«ãã€ã³ã¿ãŒ 'dp'ã®éåç §ãããå¯èœæ§ããããŸãã vfs_cache.c 1449
ãã§ãã¯ãèŠãŠãã ããïŒ
if (dp && (dp->v_flag & VISHARDLINK))
dpãã€ã³ã¿ãŒãnullã§ããå¯èœæ§ãããããšãããããŸãã ãã ããäºåæ€èšŒãªãã§ãã€ã³ã¿ãŒãéåç §ãããŸãã
if ((dp->v_flag & VROOT) || ....)
ãã©ã°ã¡ã³ãN18
åã®äŸã§ã¯ãåç §ã解é€ããåã«ãã€ã³ã¿ãŒããã§ãã¯ãããã³ãŒãå ã§ã³ãŒããå¿ãããããšããç¶æ³ã«ééããŸããã ããããå€ãã®å Žåãæåã«ãã€ã³ã¿ãŒãéåç §ãããŠãããããã§ãã¯ãããªããšããç¶æ³ã«ééããå¯èœæ§ããããŸãã XNU Kernelãããžã§ã¯ãã³ãŒããäŸå€ã§ã¯ãããŸããã§ããã ç§ãã¡ã話ããŠããããšãããããç解ããããã«ãåæäŸãèããŠã¿ãŸãããïŒ
p[n] = 1; if (!p) return false;
次ã«ããã®ãããªãšã©ãŒãå®éã«ã©ã®ããã«èŠããããèŠãŠã¿ãŸãããã ååæ¯èŒæ©èœããå§ããŸãããã æ¯èŒé¢æ°ã¯éåžžã«é°æ¹¿ã§ã :)ã
bool IORegistryEntry::compareName(....) const { const OSSymbol * sym = copyName(); bool isEqual; isEqual = sym->isEqualTo( name ); // <= if( isEqual && matched) { name->retain(); *matched = name; } if( sym) // <= sym->release(); return( isEqual ); }
PVS-StudioèŠåïŒV595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ã 'sym'ãã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªïŒ889ã896ãIORegistryEntry.cpp 889
ã// <=ããšãã圢åŒã®ã³ã¡ã³ãã§ãèå³ã®ããã³ãŒãè¡ã匷調衚瀺ããŸããã ã芧ã®ãšãããæåã¯ãã€ã³ã¿ãŒãéåç §ãããŠããŸãã ããã«ã³ãŒãã«ã¯ã nullptrãã€ã³ã¿ãŒãçãããã©ããã®ãã§ãã¯ããããŸãã ãããããã€ã³ã¿ãŒãnullã®å Žåãnullãã€ã³ã¿ãŒãéåç §ãããå®éãé¢æ°ã¯ãã®ãããªç¶æ³ã«å¯Ÿå¿ããæºåãã§ããŠããªãããšãããã«ããããŸãã
ãã©ã°ã¡ã³ãN19
ã¿ã€ããã¹ã«ããã次ã®ãšã©ãŒãçºçããŸããã
static int memorystatus_get_priority_list( memorystatus_priority_entry_t **list_ptr, size_t *buffer_size, size_t *list_size, boolean_t size_only) { .... *list_ptr = (memorystatus_priority_entry_t*)kalloc(*list_size); if (!list_ptr) { return ENOMEM; } .... }
PVS-StudioèŠåïŒV595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ã 'list_ptr'ãã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ7175ã7176ãkern_memorystatus.c 7175
ã¢ãã©ã€ã¶ãŒã¯ãæåã«å€æ°ãéæ¥åç §ãããŠããããšã確èªãã次ã®è¡ã§nullptrã®ç䟡æ§ããã§ãã¯ããŸãã ããã°ã©ããæåã*ããæžãã®ãå¿ããããããã®èå³æ·±ããšã©ãŒãçºçããŸããã å®éãã³ãŒãã¯æ¬¡ã®ããã«ãªã£ãŠããã¯ãã§ãã
*list_ptr = (memorystatus_priority_entry_t*)kalloc(*list_size); if (!*list_ptr) { return ENOMEM; }
ãšã©ãŒã¯éæ¥çã«æ€åºããããšèšããŸãã ãã ããããã¯éèŠã§ã¯ãããŸãããæãéèŠãªããšã¯ãã¢ãã©ã€ã¶ãŒãç°åžžãªã³ãŒãã«æ³šæãæãããšã©ãŒãçºçããããšã§ãã
ãã©ã°ã¡ã³ãN20-N35
XNUã«ãŒãã«ã³ãŒãã§ã¯ãV595蚺æãéããŠå€ãã®ãšã©ãŒãæ€åºãããŸãã ããããããããã¹ãŠãèããã®ã¯éå±ã§ãã ãããã£ãŠããã1ã€ã ãã±ãŒã¹ãåæãããšã©ãŒã瀺ãã¡ãã»ãŒãžã®ãªã¹ããæäŸããŸãã
inline void inp_decr_sndbytes_unsent(struct socket *so, int32_t len) { struct inpcb *inp = (struct inpcb *)so->so_pcb; struct ifnet *ifp = inp->inp_last_outifp; if (so == NULL || !(so->so_snd.sb_flags & SB_SNDBYTE_CNT)) return; if (ifp != NULL) { if (ifp->if_sndbyte_unsent >= len) OSAddAtomic64(-len, &ifp->if_sndbyte_unsent); else ifp->if_sndbyte_unsent = 0; } }
PVS-StudioèŠåïŒV595 CWE-476 nullsoã«å¯ŸããŠæ€èšŒãããåã«ãsoããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ3450ã3453ãin_pcb.c 3450
soãã€ã³ã¿ãŒã®éåœãç¬ç«ããŠè¿œè·¡ããã³ãŒããæ£ããèšè¿°ãããŠããªãããšã確èªããããšãèªè ã«ææ¡ããŸãã
ãã®ä»ã®ãšã©ãŒïŒ
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ã 'startDict'ãã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ3369ã3733ãIOService.cpp 3369
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ãããžã§ãããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ4083ã4085ãIOService.cpp 4083
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããtypeinstããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ176ã177ãOSMetaClass.cpp 176
- V595 CWE-476ãååããã€ã³ã¿ãŒã¯ãnullptrã«å¯ŸããŠæ€èšŒãããåã«äœ¿çšãããŠããŸããã è¡ã確èªããŠãã ããïŒ385ã392ãdevfs_tree.c 385
- V595 CWE-476ãã³ã¬ã¯ã·ã§ã³ããã€ã³ã¿ãŒã¯ãnullptrã«å¯ŸããŠæ€èšŒãããåã«äœ¿çšãããŠããŸããã è¡ããã§ãã¯ïŒ71ã75ãOSCollectionIterator.cpp 71
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããifpããã€ã³ã¿ãŒã䜿çšãããŸããã ãã§ãã¯è¡ïŒ2014ã2018.dlil.c 2014
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããfakeifããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ561ã566ãif_fake.c 561
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ã 'sb'ãã€ã³ã¿ãŒã䜿çšãããŸããã è¡ããã§ãã¯ïŒ138ã140ãin_pcblist.c 138
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããtpããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ2603ã2610ãtcp_subr.c 2603
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ã 'str_id'ãã€ã³ã¿ãŒã䜿çšãããŸããã è¡ããã§ãã¯ããŠãã ããïŒ1812ã1817ãkdebug.c 1812
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããsesspããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªïŒ191ã194ãsubr_prf.c 191
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããsesspããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ1463ã1469ãtty.c 1463
- V595 CWE-476 nullsoã«å¯ŸããŠæ€èšŒãããåã«ãsoããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ6714ã6719ãuipc_socket.c 6714
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããuapããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ314ã320ãnfs_upcall.c 314
- V595 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåã«ããxfromnameããã€ã³ã¿ãŒã䜿çšãããŸããã è¡ã確èªããŠãã ããïŒ3986ã4006ãkpi_vfs.c 3986
- ã泚æ å®éãç§ã¯ãã®ã¿ã€ãã®ãã¹ãŠã®èŠåã泚ææ·±ãèŠãŠããªãã ãããã£ãŠãå®éã«ã¯ãããå€ãã®ãšã©ãŒãååšããå¯èœæ§ããããŸãã
ãã©ã°ã¡ã³ãN36ãN37
ãããŠãnullãã€ã³ã¿ãŒã®äœ¿çšã«é¢ããæåŸã®ããã€ãã®ééãã
static void feth_start(ifnet_t ifp) { .... if_fake_ref fakeif; .... if (fakeif != NULL) { peer = fakeif->iff_peer; flags = fakeif->iff_flags; } /* check for pending TX */ m = fakeif->iff_pending_tx_packet; .... }
PVS-StudioèŠåïŒV1004 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåŸããfakeifããã€ã³ã¿ãŒãå®å šã«äœ¿çšãããŸããã§ããã è¡ã確èªããŠãã ããïŒ566ã572ãif_fake.c 572
ãã®ã³ãŒãã«ã³ã¡ã³ãããå¿ èŠã¯ãªããšæããŸãã fakeifãã€ã³ã¿ãŒãã©ã®ããã«ãã§ãã¯ããã䜿çšããããã確èªããŠãã ããã
æåŸã®åæ§ã®ã±ãŒã¹ïŒV1004 CWE-476 nullptrã«å¯ŸããŠæ€èšŒãããåŸããrt-> rt_ifpããã€ã³ã¿ãŒãå®å šã«äœ¿çšãããŸããã§ããã è¡ã確èªããŠãã ããïŒ138ã140ãnetsrc.c 140
CWE-119ïŒã¡ã¢ãªãããã¡ãŒã®å¢çå ã§ã®æäœã®äžé©åãªå¶é
ãããã¡ã®å¢çãè¶ããããšã«é¢é£ãããšã©ãŒãããã€ããããŸããã XNU Kernelã®ãããªéèŠãªãããžã§ã¯ãã®éåžžã«äžå¿«ãªééãã
æµ·å€ã«è¡ãããã®ããŸããŸãªãªãã·ã§ã³ã¯ãããŸããŸãªCWE IDã«ãã£ãŠåé¡ã§ããŸããããã®å Žåãã¢ãã©ã€ã¶ãŒã¯CWE-119ãéžæããŸããã
ãã©ã°ã¡ã³ãN38
æåã«ãããã€ãã®ãã¯ããã©ã®ããã«å®£èšãããŠããããèŠãŠã¿ãŸãããã
#define IFNAMSIZ 16 #define IFXNAMSIZ (IFNAMSIZ + 8) #define MAX_ROUTE_RULE_INTERFACES 10
次ã®ããšãèŠããŠããããšãéèŠã§ãã
- IFXNAMSIZ = 24
- MAX_ROUTE_RULE_INTERFACES = 10
次ã«ã snprintfé¢æ°ãšmemseté¢æ°ã䜿çšãããšãã«ããããã¡ãŒã®å¢çãè¶ããããšãã§ããé¢æ°ãèããŸãã ã€ãŸã 2ã€ã®ãšã©ãŒãçºçããŸãã
static inline const char * necp_get_result_description(....) { .... char interface_names[IFXNAMSIZ][MAX_ROUTE_RULE_INTERFACES]; .... for (index = 0; index < MAX_ROUTE_RULE_INTERFACES; index++) { if (route_rule->exception_if_indices[index] != 0) { ifnet_t interface = ifindex2ifnet[....]; snprintf(interface_names[index], IFXNAMSIZ, "%s%d", ifnet_name(interface), ifnet_unit(interface)); } else { memset(interface_names[index], 0, IFXNAMSIZ); } } .... }
PVS-Studioã®èŠåïŒ
- V512 CWE-119ã__builtin___memcpy_chkãé¢æ°ãåŒã³åºããšããããã¡ãŒãªãŒããŒãããŒãçºçããŸãã -çŸåšã®necp_client.c 1459ã§è¿œå
- V557 CWE-787ã¢ã¬ã€ã®ãªãŒããŒã©ã³ãå¯èœã§ãã 'length-1'ã€ã³ããã¯ã¹ã®å€ã¯23ã«éããå¯èœæ§ããããŸãã-çŸåšã®è¿œå necp_client.c 1460
interface_namesã® 2次å é åãã©ã®ããã«å®£èšãããŠãããã«æ³šç®ããŠãã ããã
char interface_names[IFXNAMSIZ][MAX_ROUTE_RULE_INTERFACES]; // : char interface_names[24][10];
ãã ãããã®é åã¯æ¬¡ã®ããã«äœ¿çšãããŸãã
char interface_names[MAX_ROUTE_RULE_INTERFACES][IFXNAMSIZ]; // : char interface_names[10][24];
ããŒã¿ããäœããã®æ··ä¹±ãçããŠããããšãããããŸãã
èããããšãªãã誰ããå¿é ããå¿ èŠã¯ãªããšèšããããããŸããããªããªããäž¡æ¹ã®é åãåããã€ãæ°ãå æããŠããããã§ãã
ãããããã¹ãŠãæªãã§ãã interface_names [10..23] [....]é åã®èŠçŽ ã¯ãã«ãŒãå ã®ã€ã³ããã¯ã¹å€æ°ãå€[0..9]ããšãããã䜿çšãããŸããã ãããã interface_names [0..9] [....]ã®èŠçŽ ã¯ãäºãã«ãéè€ããå§ããŸãã ã€ãŸã äžéšã®ããŒã¿ã¯ä»ã®ããŒã¿ãäžæžãããŸãã
çµæã¯å®å šãªã§ãããã§ãã é åã®äžéšã¯åæåãããã«æ®ããä»ã®éšåã«ã¯æ¢ã«èšé²ãããããŒã¿ã®äžã«ããŒã¿ãæžã蟌ãŸãããšãã®æ··ä¹±ãå«ãŸããŠããŸãã
ãã©ã°ã¡ã³ãN39
åããã¡ã€ã«necp_client.cã®äžã«ã¯ãéåžžã«ãã䌌ããšã©ãŒãå«ãå¥ã®é¢æ°ããããŸãã
#define IFNAMSIZ 16 #define IFXNAMSIZ (IFNAMSIZ + 8) #define NECP_MAX_PARSED_PARAMETERS 16 struct necp_client_parsed_parameters { .... char prohibited_interfaces[IFXNAMSIZ] [NECP_MAX_PARSED_PARAMETERS]; .... }; static int necp_client_parse_parameters(...., struct necp_client_parsed_parameters *parsed_parameters) { .... u_int32_t length = ....; .... if (length <= IFXNAMSIZ && length > 0) { memcpy(parsed_parameters->prohibited_interfaces[ num_prohibited_interfaces], value, length); parsed_parameters->prohibited_interfaces[ num_prohibited_interfaces][length - 1] = 0; .... }
PVS-StudioèŠåïŒ
- V512 CWE-119ã__builtin___memcpy_chkãé¢æ°ãåŒã³åºããšããããã¡ãŒãªãŒããŒãããŒãçºçããŸãã-çŸåšã®necp_client.c 1459ã§è¿œå
- V557 CWE-787ã¢ã¬ã€ã®ãªãŒããŒã©ã³ãå¯èœã§ãã'length-1'ã€ã³ããã¯ã¹ã®å€ã¯23ã«éããå¯èœæ§ããããŸãã-çŸåšã®è¿œå necp_client.c 1460
ãã¹ãŠåãã§ããé åïŒ
char prohibited_interfaces[IFXNAMSIZ][NECP_MAX_PARSED_PARAMETERS];
次ã®ããã«åŠçãããŸãã
char prohibited_interfaces[NECP_MAX_PARSED_PARAMETERS][IFXNAMSIZ];
CWE-563ïŒäœ¿çšããªãå€æ°ãžã®å²ãåœãŠ
PVS-Studioã«ãã£ãŠæ€åºãããCWE-563ã®æ¬ é¥ã¯ãå€ãã®å Žåãã¿ã€ããã¹ã®çµæã§ããããã§ããã®ãããªçŸããã¿ã€ããã¹ãæ€èšããŸãã
ãã©ã°ã¡ã³ãN40
uint32_t gss_krb5_3des_unwrap_mbuf(....) { .... for (cflag = 1; cflag >= 0; cflag--) { *minor = gss_krb5_3des_token_get( ctx, &itoken, wrap, &hash, &offset, &length, reverse); if (*minor == 0) break; wrap.Seal_Alg[0] = 0xff; wrap.Seal_Alg[0] = 0xff; } .... }
PVS-StudioèŠåïŒV519 CWE-563 'wrap.Seal_Alg [0]'å€æ°ã«ã¯å€ãé£ç¶ããŠ2åå²ãåœãŠãããŸãã ããããããã¯ééãã§ããè¡ã確èªããŠãã ããïŒ2070ã2071ãgss_krb5_mech.c 2071
2åãå€0xffãé åã®åãèŠçŽ ã«æžã蟌ã¿ãŸããç§ã¯é£ã®ã³ãŒããèŠãŠãæ¬åœã«ããã«æžãããã£ããšããçµè«ã«éããŸããïŒ
wrap.Seal_Alg[0] = 0xff; wrap.Seal_Alg[1] = 0xff;
é¢æ°ã®ååããå€æãããšããããã¯ãŒã¯èªèšŒãããã³ã«ã«é¢é£ä»ããããŠããŸãããããŠããã®ãããªå€±æ ...ãªããŠæãããããšã§ããããããã§
PVS-Studioãè³Œå ¥ã§ããŸããåœç€Ÿã®ã¢ãã©ã€ã¶ãŒã¯ããã®ãããªå€ãã®ãšã©ãŒã®é²æ¢ã«åœ¹ç«ã¡ãŸãïŒ
ãã©ã°ã¡ã³ãN41ãN42ãN43ãN44
static struct mbuf * pf_reassemble(struct mbuf *m0, struct pf_fragment **frag, struct pf_frent *frent, int mff) { .... m->m_pkthdr.csum_flags &= ~CSUM_PARTIAL; m->m_pkthdr.csum_flags = CSUM_DATA_VALID | CSUM_PSEUDO_HDR | CSUM_IP_CHECKED | CSUM_IP_VALID; .... }
PVS-StudioèŠåïŒV519 CWE-563ãm-> M_dat.MH.MH_pkthdr.csum_flagsãå€æ°ã«ã¯ãå€ãé£ç¶ããŠ2åå²ãåœãŠãããŸãã ããããããã¯ééãã§ããè¡ã確èªããŠãã ããïŒ758ã759ãpf_norm.c 759
è¡ïŒ
m->m_pkthdr.csum_flags &= ~CSUM_PARTIAL;
å®çšçã§ã¯ãããŸããã次ã®è¡ã§ã¯ãå€æ°m-> m_pkthdr.csum_flagsã«æ°ããå€ãå²ãåœãŠãããŸããæ£ããã³ãŒããå®éã«ã©ã®ããã«èŠãããã¯ããããŸããããã|ãæåãå¿ããŠããŸã£ããšæããŸããç§ã®è¬èãªæèŠã§ã¯ãã³ãŒãã¯æ¬¡ã®ããã«ãªããŸãã
m->m_pkthdr.csum_flags &= ~CSUM_PARTIAL; m->m_pkthdr.csum_flags |= CSUM_DATA_VALID | CSUM_PSEUDO_HDR | CSUM_IP_CHECKED | CSUM_IP_VALID;
åæ§ã®ãšã©ãŒã瀺ãèŠåãããã«3ã€ãããŸãã
- V519 CWE-563ãm-> M_dat.MH.MH_pkthdr.csum_flagsãå€æ°ã«ã¯ãé£ç¶ããŠ2åå€ãå²ãåœãŠãããŸãã ããããããã¯ééãã§ãã è¡ã確èªããŠãã ããïŒ1349ã1350ãpf_norm.c 1350
- V519 CWE-563ãm-> M_dat.MH.MH_pkthdr.csum_flagsãå€æ°ã«ã¯ãé£ç¶ããŠ2åå€ãå²ãåœãŠãããŸãã ããããããã¯ééãã§ãã è¡ããã§ãã¯ïŒ2984ã2985ãip_input.c 2985
- V519 CWE-563ãm-> M_dat.MH.MH_pkthdr.csum_flagsãå€æ°ã«ã¯ãé£ç¶ããŠ2åå€ãå²ãåœãŠãããŸãã ããããããã¯ééãã§ãã è¡ããã§ãã¯ïŒ773ã774ãfrag6.c 774
CWE-14ïŒã³ã³ãã€ã©ãŒãã³ãŒããåé€ããŠãããã¡ãŒãã¯ãªã¢ãã
ãããã°ããŒãžã§ã³ã§ã¯èŠããªããéåžžã«æ²¹æã®ãªããªãæ¬ é¥ãèªè ãããããŸã ããç¥ããªãå Žåã¯ãèªã¿ç¶ããåã«ã次ã®ãªã³ã¯ãèªãããšããå§ãããŸãã
- å人ããŒã¿ã®å®å šãªæ¶å»ã
- V597ãã³ã³ãã€ã©ã¯ããFooããããã¡ããã©ãã·ã¥ããããã«äœ¿çšããããmemsetãé¢æ°åŒã³åºããåé€ã§ããŸããRtlSecureZeroMemoryïŒïŒé¢æ°ã䜿çšããŠããã©ã€ããŒãããŒã¿ãæ¶å»ããå¿ èŠããããŸãã
- CWE-14ïŒã³ã³ãã€ã©ããããã¡ãã¯ãªã¢ããã³ãŒããåé€ã
èªè ãã¡ã¢ãªã«ä¿åãããŠãããã©ââã€ããŒãããŒã¿ãäžæžãããçç±ãç解ããŠããªãå Žåã¯ãèšäºãã¡ã¢ãªãäžæžããã-ãªãïŒãããå§ãããŸãã
ãã®ãããã¡ã¢ãªå ã®ãã©ã€ããŒãããŒã¿ãäžæžãããããšã¯éèŠã§ãããã³ã³ãã€ã©ã¯å¯Ÿå¿ããã³ãŒããåé€ããããšããããŸããããã¯ããã®èŠ³ç¹ããèŠããšäœåãªããã§ããXNU Kernelã®èå³æ·±ããšãããèŠãŠã¿ãŸãããã
ãã©ã°ã¡ã³ãN45
__private_extern__ void YSHA1Final(unsigned char digest[20], YSHA1_CTX* context) { u_int32_t i, j; unsigned char finalcount[8]; .... /* Wipe variables */ i = j = 0; memset(context->buffer, 0, 64); memset(context->state, 0, 20); memset(context->count, 0, 8); memset(finalcount, 0, 8); // <= #ifdef SHA1HANDSOFF YSHA1Transform(context->state, context->buffer); #endif }
PVS-StudioèŠåïŒV597 CWE-14ã³ã³ãã€ã©ãŒã¯ããfinsetããããã¡ãŒããã©ãã·ã¥ããããã«äœ¿çšããããmemsetãé¢æ°åŒã³åºããåé€ã§ããŸãããã©ã€ããŒãããŒã¿ãæ¶å»ããã«ã¯ãmemset_sïŒïŒé¢æ°ã䜿çšããå¿ èŠããããŸãã sha1mod.c 188
ãªãªãŒã¹ããŒãžã§ã³ãæé©åããããã«ãã³ã³ãã€ã©ã¯ãã³ã¡ã³ãã// <=ãã§æžãçããã³ãŒãè¡ãåé€ããæš©å©ãæã£ãŠããŸããã»ãŒééããªã圌ã¯ããããã§ãããã
ãã©ã°ã¡ã³ãN46
__private_extern__ void YSHA1Transform(u_int32_t state[5], const unsigned char buffer[64]) { u_int32_t a, b, c, d, e; .... state[0] += a; state[1] += b; state[2] += c; state[3] += d; state[4] += e; /* Wipe variables */ a = b = c = d = e = 0; }
PVS-StudioèŠåïŒV1001 CWE-563ãaãå€æ°ãå²ãåœãŠãããŠããŸãããé¢æ°ã®æåŸãŸã§äœ¿çšãããŸãããsha1mod.c 120
ã³ã³ãã€ã©ã«ã¯ãå€æ°ãé¢æ°ã§äœ¿çšãããªããªã£ããããå€æ°ããªã»ããããã³ãŒããçæããªãæš©å©ããããŸãã
PVS-Studioã¢ãã©ã€ã¶ãŒããã®çãããç¶æ³ãCWE-563ãšè§£éããããšã«æ³šæããŠãã ãããå®éãåãæ¬ é¥ãç°ãªãCWEãšããŠè§£éãããããšãããããããã®å Žåãã¢ãã©ã€ã¶ãŒã¯CWE-563ãéžæããŸããããã ãããã®ã³ãŒãã®äœãåé¡ãªã®ããããæ£ç¢ºã«èª¬æããããããã®ã³ãŒãã¯ç¹ã«CWE-14ã«èµ·å ãããšå€æããŸããã
CWE-783ïŒæŒç®ååªå ããžãã¯ãšã©ãŒ
CWE-783ã®æ¬ é¥ã¯ãããã°ã©ããŒãæäœã®åªå é äœãæ··åããæå³ãããšããã«åäœããªãã³ãŒããèšè¿°ããå Žåã«çºçããŸããå€ãã®å Žåããã®ãããªãšã©ãŒã¯äžæ³šæãŸãã¯æ¬åŒ§ã®æ¬ èœã«ããçºçããŸãã
ãã©ã°ã¡ã³ãN47
int getxattr(....) { .... if ((error = copyinstr(uap->attrname, attrname, sizeof(attrname), &namelen) != 0)) { goto out; } .... out: .... return (error); }
PVS-StudioèŠåïŒV593 CWE-783ãA = BïŒ= Cãã®è¡šçŸãæ€èšããããšãæ€èšããŠãã ãããåŒã¯æ¬¡ã®ããã«èšç®ãããŸãïŒ 'A =ïŒBïŒ= CïŒ'ãvfs_syscalls.c 10574
å€å žçãªãšã©ãŒãç§ã¯ããŸããŸãªããã°ã©ã ã§ãã®ãããªãšã©ãŒã«ééããŸãïŒèšŒæ ïŒãæ ¹æ¬çãªåå ã¯ããªãããã®çç±ã§äžéšã®ããã°ã©ããŒã1è¡ã«å€ãè©°ã蟌ãåŸåãããããšã§ãã
ãã®çµæã次ã®ä»£ããã«ïŒ
Status s = foo(); if (s == Error) return s;
圌ãã¯æžãïŒ
Status s; if (s = foo() == Error) return s;
ãŸããã³ãŒãã«ãšã©ãŒãçºçããŸãã
- ããã°ã©ãã¯ãåŒã次ã®ããã«è©äŸ¡ãããããšãæåŸ ããŠããŸããïŒs = fooïŒïŒïŒ==ãšã©ãŒã
- å®éãåŒã¯s =ïŒfooïŒïŒ== ErrorïŒã«è©äŸ¡ãããŸãã
ãã®çµæãreturnã¹ããŒãã¡ã³ãã¯Errorå®æ°ã«çããå€ã§ã¯ãªãã1ã®ç¡å¹ãªãšã©ãŒã¹ããŒã¿ã¹ãè¿ããŸãã
ç§ã¯å®æçã«ãã®ãããªã³ãŒããæ¹å€ããŠãããäžåºŠã«è€æ°ã®ã¢ã¯ã·ã§ã³ã1è¡ã«ããã·ã¥ããªãããšããå§ãããŸãããããã·ã¥ãã¯ã³ãŒãã®ãµã€ãºãå€§å¹ ã«ã¯åæžããŸããããããŸããŸãªãšã©ãŒãåŒãèµ·ãããŸããããã«ã€ããŠã¯ãç§ã®ããããã¯ãããã°ã©ãã³ã°ããªãã¡ã¯ã¿ãªã³ã°ããã®ä»ãã¹ãŠã®äž»ãªåé¡ãã§è©³ããèªãããšãææ¡ããŸããç« ãåç §ããŠãã ããã
- 11.ã³ãŒãã®è¡ã貪欲ã«ããªãã§ãã ãã
- 16.ãã©ãããã°ãããã-ããã°ã©ãã³ã°ã§ã¯åãå ¥ããããªã
XNU Kernelã®ã³ãŒãã«æ»ããŸãããããšã©ãŒã®å Žåãgetxattré¢æ°ã¯ãå®éã®ãšã©ãŒã³ãŒãã§ã¯ãªããå€1ãè¿ããŸãã
ãã©ã°ã¡ã³ãN48-N52
static void memorystatus_init_snapshot_vmstats( memorystatus_jetsam_snapshot_t *snapshot) { kern_return_t kr = KERN_SUCCESS; mach_msg_type_number_t count = HOST_VM_INFO64_COUNT; vm_statistics64_data_t vm_stat; if ((kr = host_statistics64(.....) != KERN_SUCCESS)) { printf("memorystatus_init_jetsam_snapshot_stats: " "host_statistics64 failed with %d\n", kr); memset(&snapshot->stats, 0, sizeof(snapshot->stats)); } else { + .... }
PVS-StudioèŠåïŒV593 CWE-783ãA = BïŒ= Cãã®è¡šçŸãæ€èšããããšãæ€èšããŠãã ãããåŒã¯æ¬¡ã®ããã«èšç®ãããŸãïŒ 'A =ïŒBïŒ= CïŒ'ã kern_memorystatus.c 4554 kr
å€æ°ã«å²ãåœãŠãããšãã§ããå€ã¯2ã€ã®ã¿ã§ãã0ãŸãã¯1ã§ãããã®ãããprintfé¢æ°ã¯host_statistics64é¢æ°ã«ãã£ãŠè¿ãããå®éã®ã¹ããŒã¿ã¹ã§ã¯ãªããåžžã«æ°å€1ãåºåããŸããèšäºã¯å€§ããã§ããç§ã¯åœŒå¥³ã ãã§ãªããèªè ãéå±ããããšæããŸãããããã£ãŠããã®èšäºã§æ€èšãããã©ã°ã¡ã³ãã®æ°ãæžãããŸããä»ã®åæ§ã®æ¬ é¥ã¯èæ ®ããã®ã«é¢çœããªãã§ãããããŠãç§ã¯ã¡ãã»ãŒãžã®ãªã¹ãã«èªåèªèº«ãå¶éããŸãïŒ
- V593 CWE-783 Consider reviewing the expression of the 'A = B != C' kind. The expression is calculated as following: 'A = (B != C)'. vfs_syscalls.c 10654
- V593 CWE-783 Consider reviewing the expression of the 'A = B != C' kind. The expression is calculated as following: 'A = (B != C)'. vfs_syscalls.c 10700
- V593 CWE-783 Consider reviewing the expression of the 'A = B != C' kind. The expression is calculated as following: 'A = (B != C)'. vfs_syscalls.c 10759
- V593 CWE-783 Consider reviewing the expression of the 'A = B != C' kind. The expression is calculated as following: 'A = (B != C)'. kern_exec.c 2297
CWE-758: Reliance on Undefined, Unspecified, or Implementation-Defined Behavior
CãŸãã¯C ++ããã°ã©ã ã§æªå®çŸ©ãŸãã¯æªæå®ã®åäœãååŸããæ¹æ³ã¯ãããããããŸãããããã£ãŠãPVS-Studioã¢ãã©ã€ã¶ãŒã¯ãV567ãV610ãV611ãV681ãV704ãV708ãV726ãV736ãªã©ã®åé¡ãç¹å®ããããšãç®çãšããå€ãã®èšºæãå®è£ ããŠããŸãã
XNUã®å Žåãã¢ãã©ã€ã¶ãŒã¯ãè² ã®æ°å€ã®ã·ããã«ãã£ãŠåŒãèµ·ããããæªå®çŸ©ã®åäœã«é¢é£ããCWE-758ã® 2ã€ã®åŒ±ç¹ã®ã¿ãæ€åºããŸããã
ãã©ã°ã¡ã³ãN53ãN54
static void pfr_prepare_network(union sockaddr_union *sa, int af, int net) { .... sa->sin.sin_addr.s_addr = net ? htonl(-1 << (32-net)) : 0; .... }
PVS-StudioèŠåïŒV610 CWE-758æªå®çŸ©ã®åäœãã·ããæŒç®åã<<ãã確èªããŠãã ãããå·Šã®ãªãã©ã³ã '-1'ã¯è² ã§ããpf_table.c 976
è² ã®æ°ãå·Šã«ã·ãããããšãæªå®çŸ©ã®åäœãçºçããŸããå®éã«ã¯ããã®ã³ãŒãã¯ããã°ã©ããæåŸ ãããšããã«åäœããå¯èœæ§ããããŸããããã§ãããã®ã³ãŒãã¯æ£ãããªããããä¿®æ£ããå¿ èŠããããŸããããã¯æ¬¡ã®ããã«å®è¡ã§ããŸãã
htonl((unsigned)(-1) << (32-net))
PVS-Studioã¢ãã©ã€ã¶ãŒã¯ãããã§å¥ã®å€åãèŠã€ããŸãïŒV610 CWE-758æªå®çŸ©ã®åäœãã·ããæŒç®åã<<ãã確èªããŠãã ãããå·Šã®ãªãã©ã³ã '-1'ã¯è² ã§ããpf_table.c 983
CWE-401ïŒæåŸã®åç §ãåé€ããåã®ã¡ã¢ãªã®äžé©åãªãªãªãŒã¹ïŒãã¡ã¢ãªãªãŒã¯ãïŒ
XNU Kernelã®éçºè ã¯ãã¢ãã©ã€ã¶ãŒãã¡ã¢ãªãªãŒã¯ïŒCWE-401ïŒã®åé¡ãèŠã€ããããšãã§ããªãã£ããšããäºå®ãè³è³ãã¹ãã§ããåé€æŒç®åããªããžã§ã¯ãåæåãšã©ãŒã§åŒã³åºãããªãå Žåãçãããå Žæã¯3ã€ã ãã§ãããã ãããããæ£ç¢ºã«ééãã§ãããã©ããã¯ããããŸããã
ãã©ã°ã¡ã³ãN55ãN56ãN57
IOService * IODTPlatformExpert::createNub(IORegistryEntry * from) { IOService * nub; nub = new IOPlatformDevice; if (nub) { if( !nub->init( from, gIODTPlane )) { nub->free(); nub = 0; } } return (nub); }
V773 CWE-401ãnubããã€ã³ã¿ãŒã«ã¯ãã¡ã¢ãªãŒã解æŸããã«å€ã2åå²ãåœãŠãããŸãããã¡ã¢ãªãªãŒã¯ãçºçããå¯èœæ§ããããŸããIOPlatformExpert.cpp 1287 init
é¢æ°ããªããžã§ã¯ããåæåã§ããªãå Žåãã¡ã¢ãªãªãŒã¯ãçºçããå¯èœæ§ããããŸããç§ã®æèŠã§ã¯ãåé€æŒç®åã¯ããã«ãããŸããã次ã®ããã«æžãããŠããã¯ãã§ãã
if( !nub->init( from, gIODTPlane )) { nub->free(); delete nub; nub = 0; }
ç§ãæ£ãããã©ããã¯ããããŸããããããããfreeé¢æ°èªäœãããdelete * this;ããšããæäœãå®è¡ããŠãªããžã§ã¯ããç Žæ£ããŸãããããã®èŠåã«å°éããé ã«ã¯ãã§ã«ç²ããŠããã®ã§ãç§ã¯æ³šææ·±ãç解ããŠããŸããã§ããã
åæ§ã®ã¢ãã©ã€ã¶ãŒèŠåïŒ
- V773 CWE-401ãinstããã€ã³ã¿ãŒã«ãã¡ã¢ãªãŒã解æŸããã«å€ã2åå²ãåœãŠãããŸãããã¡ã¢ãªãªãŒã¯ãçºçããå¯èœæ§ããããŸããIOUserClient.cpp 246
- V773 CWE-401ãmyselfããã€ã³ã¿ãŒã«ã¯ãã¡ã¢ãªãŒã解æŸããã«å€ã2åå²ãåœãŠãããŸãããã¡ã¢ãªãªãŒã¯ãçºçããå¯èœæ§ããããŸããIOPMrootDomain.cpp 9151
CWE-129ïŒé åã€ã³ããã¯ã¹ã®äžé©åãªæ€èšŒ
CWE-129ã®æ¬ é¥ã¯ãé åå ã®èŠçŽ ã«ã€ã³ããã¯ã¹ãä»ããããã«äœ¿çšãããå€æ°ã誀ã£ãŠããŸãã¯äžååã«ãã§ãã¯ãããŠããããšã瀺ããŠããŸãããã®çµæãé åã®ãªãŒããŒãããŒãçºçããå¯èœæ§ããããŸãã
ãã©ã°ã¡ã³ãN58-N61
IOReturn IOStateReporter::updateChannelValues(int channel_index) { .... state_index = _currentStates[channel_index]; if (channel_index < 0 || channel_index > (_nElements - state_index) / _channelDimension) { result = kIOReturnOverrun; goto finish; } .... }
PVS-StudioèŠåïŒV781 CWE-129ãchannel_indexãå€æ°ã®å€ã¯ã䜿çšåŸã«ãã§ãã¯ãããŸãããããããããã°ã©ã ããžãã¯ã«ééãããããŸããè¡ã確èªããŠãã ããïŒ852ã855ãIOStateReporter.cpp 852
è² ã®å€ã«å¯Ÿããä¿è·ã誀ã£ãŠå®è£ ãããŠããŸããæåã«ãèŠçŽ ã¯åžžã«é åããååŸãããã€ã³ããã¯ã¹ãè² ã§ãªãããšã®æ€èšŒã®ã¿ãè¡ãããŸãã
ãã®ã³ãŒãã¯æ¬¡ã®ããã«æžãçŽãã¹ãã ãšæããŸãã
IOReturn IOStateReporter::updateChannelValues(int channel_index) { .... if (channel_index < 0) { result = kIOReturnOverrun; goto finish; } state_index = _currentStates[channel_index]; if (channel_index > (_nElements - state_index) / _channelDimension) { result = kIOReturnOverrun; goto finish; } .... }
ãããããchannel_indexã®å€ãé åã®ãµã€ãºãè¶ ããªãããã«ãããã§ãã¯ãè¿œå ããå¿ èŠããããŸããç§ã¯ã³ãŒãã«è©³ãããªãã®ã§ãXNU Kerneléçºè ã®è£éã«ä»»ããŸãã
åæ§ã®ãšã©ãŒïŒ
- V781 CWE-129ãchannel_indexãå€æ°ã®å€ã¯ã䜿çšåŸã«ãã§ãã¯ãããŸãããããããããã°ã©ã ããžãã¯ã«ééãããããŸããè¡ã確èªããŠãã ããïŒ651ã654ãIOStateReporter.cpp 651
- V781 CWE-129ãpriãå€æ°ã®å€ã¯ã䜿çšåŸã«ãã§ãã¯ãããŸãããããããããã°ã©ã ããžãã¯ã«ééãããããŸããè¡ã確èªããŠãã ããïŒ267ã269ãpktsched_fq_codel.c 267
- V781 CWE-129ãpcidãå€æ°ã®å€ã¯ã䜿çšåŸã«ãã§ãã¯ãããŸãããããããããã°ã©ã ããžãã¯ã«ééãããããŸããè¡ã確èªããŠãã ããïŒ224ã225ãpmap_pcid.c 224
CWE-480ïŒäžé©åãªæŒç®åã®äœ¿çš
CWE-480ã®æ¬ é¥ã¯ãéåžžãåŒã®äœããã®ã¿ã€ããã¹ã«é¢é£ä»ããããŠããŸããååãšããŠããããã¯ããŸãå€ããããŸããããéåžžã«é¢çœãã§ãããã®ãããªãšã©ãŒãèŠãŠãã©ã®ããã«ããããäœæã§ããã®ãçåã«æããŸããããã§ããèšäºã§ç¹°ãè¿ã瀺ããããã«ãé«åºŠãªè³æ Œãæã€ããã°ã©ããŒã§ããããã®ãããªãšã©ãŒããå ããŸããã
ãã©ã°ã¡ã³ãN62
#define NFS_UC_QUEUE_SLEEPING 0x0001 static void nfsrv_uc_proxy(socket_t so, void *arg, int waitflag) { .... if (myqueue->ucq_flags | NFS_UC_QUEUE_SLEEPING) wakeup(myqueue); .... }
PVS-StudioèŠåïŒV617 CWE-480ç¶æ ã®æ€æ»ãæ€èšããŠãã ãããã|ãã®ã0x0001ãåŒæ° ãããåäœæŒç®ã«ãŒã以å€ã®å€ãå«ãŸããŠããŸããnfs_upcall.c 331
äžéšã®ãšã³ãã£ãã£ã¯ãå¿ èŠä»¥äžã«é »ç¹ã«ãèµ·åãããŸããããããç¶æ ã«é¢ä¿ãªããåžžã«ãç®èŠãããŸããã»ãšãã©ã®å Žåã次ã®ããã«èšè¿°ããå¿ èŠããããŸãã
if (myqueue->ucq_flags & NFS_UC_QUEUE_SLEEPING) wakeup(myqueue);
CWE-665ïŒäžé©åãªåæå
PVS-Studioã¢ãã©ã€ã¶ãŒã¯ãCWEã«åŸã£ãŠæ¬¡ã®ãšã©ãŒãåé¡ã§ããŸããã§ãããç§ã®æèŠã§ã¯ãç§ãã¡ã¯CWE-665ãæ±ã£ãŠããŸãã
ãã©ã°ã¡ã³ãN63
extern void bzero(void *, size_t); static struct thread thread_template, init_thread; struct thread { .... struct thread_qos_override { struct thread_qos_override *override_next; uint32_t override_contended_resource_count; int16_t override_qos; int16_t override_resource_type; user_addr_t override_resource; } *overrides; .... }; void thread_bootstrap(void) { .... bzero(&thread_template.overrides, sizeof(thread_template.overrides)); .... }
PVS-StudioèŠåïŒV568 'sizeofïŒïŒ'æŒç®åãã¯ã©ã¹ãžã®ãã€ã³ã¿ãŒã®ãµã€ãºãè©äŸ¡ããã®ã¯å¥åŠã§ããã 'thread_template.overrides'ã¯ã©ã¹ãªããžã§ã¯ãã®ãµã€ãºã¯è©äŸ¡ããŸãããthread.c 377
ãã€ã³ã¿ãŒãæ ŒçŽããå€æ°ã®ã¢ãã¬ã¹ãååŸããbzeroé¢æ°ã䜿çšããŠãã®å€æ°ããªã»ããããŸããå®éã圌ãã¯ãã€ã³ã¿ã«nullptrãæžã蟌ãã ã ãã§ãã
é¢æ°bzeroã䜿çšããããšã¯ãå€æ°ãç¡å¹ã«ããéåžžã«å¥åŠãªäžèªç¶ãªæ¹æ³ã§ããæžãã®ããã£ãšç°¡åã§ããïŒ
thread_template.overrides = NULL;
ããããããããã¡ããªã»ãããããã誀ã£ãŠãã€ã³ã¿ããªã»ããããããšçµè«ä»ããŸãããã€ãŸããæ£ããã³ãŒãã¯æ¬¡ã®ããã«ãªã£ãŠããã¯ãã§ãã
bzero(thread_template.overrides, sizeof(*thread_template.overrides));
CWE-691ïŒäžååãªå¶åŸ¡ãããŒç®¡ç
CWE-691ã¯ãåœä»€ã·ãŒã±ã³ã¹ã®ç°åžžã瀺ããŸããå¥ã®ç°åžžãèããããŸã-ã³ãŒãã®èšèšãåäœæ¹æ³ãšäžèŽããŸãããããã¯ãXNU Kernelã³ãŒãã§åºäŒã£ããŸãã«ãã®ã±ãŒã¹ã§ãã
Fragment N64
HoorayãæåŸã®ã³ãŒããèæ ®ããå¿ èŠããããŸããïŒã¢ãã©ã€ã¶ãŒã«ãã£ãŠçºè¡ãããã¬ããŒããèŠããšãã«æ°ã¥ããªãã£ãä»ã®ãšã©ãŒããããããããŸããããã§ããã ãå€ãã®ãšã©ãŒãç¹å®ãããšããç®æšããªãã£ãããšãæãåºããŸãããããã«ãããXNU Kernelã®éçºè ã¯ãããžã§ã¯ãã³ãŒãã«ç²ŸéããŠãããããç§ãããã¬ããŒããç 究ããããšãã§ããŸããããã§ã¯ãçŸããæ°åã®64ã«ã€ããŠèããŠã¿ãŸãããããã®æ°åã¯ããµã€ãviva64ã®ååãšäžèŽããŠããŸãã
ã泚æãviva64ãã®ç±æ¥ã«èå³ã®ããæ¹ã¯ããPVS-Studioãããžã§ã¯ãã10幎åã«ã©ã®ããã«å§ãŸã£ããããšããèšäºãèªãããšããå§ãããŸãã
void vm_page_release_startup(vm_page_t mem); void pmap_startup( vm_offset_t *startp, vm_offset_t *endp) { .... // -debug code remove if (2 == vm_himemory_mode) { for (i = 1; i <= pages_initialized; i++) { .... } } else // debug code remove- /* * Release pages in reverse order so that physical pages * initially get allocated in ascending addresses. This keeps * the devices (which must address physical memory) happy if * they require several consecutive pages. */ for (i = pages_initialized; i > 0; i--) { if(fill) fillPage(....); vm_page_release_startup(&vm_pages[i - 1]); } .... }
PVS-StudioèŠåïŒV705 CWE-691ãelseããããã¯ãå¿ãããããã³ã¡ã³ãã¢ãŠãããããããŠãããã°ã©ã ã®åäœããžãã¯ãå€æŽãããå¯èœæ§ããããŸããvm_resident.c 1248
ããããããã«ã¯ãšã©ãŒã¯ãããŸãããããããelseããŒã¯ãŒãã¯æ¬åœã«ç§ãæ··ä¹±ãããŸããã³ãŒãã¯ãã«ãŒããåžžã«å®è¡ãããŠããããã«èŠããããã«èšèšãããŠããŸããå®éãæ¡ä»¶ïŒ2 == vm_himemory_modeïŒãfalseã®å Žåã«ã®ã¿ãã«ãŒããå®è¡ãããŸãã
ãããã«
macOSã®äžçã§ã¯ãæ°ãã匷åãªéçã³ãŒãã¢ãã©ã€ã¶ãŒã§ããPVS-StudioããCããã³C ++ããã°ã©ã ã®ãšã©ãŒãšæœåšçãªè匱æ§ãæ€åºã§ããŸããç§ãã¡ã®ã¢ãã©ã€ã¶ãŒãããããã®ãããžã§ã¯ãã§è©ŠããŠããã®æ©èœãè©äŸ¡ããŠãã ããã
ãæž èŽããããšãããããŸãããPVS-StudioãmacOSã§å©çšå¯èœã«ãªã£ããšããæ å ±ãååãšå ±æããããšãå¿ããªãã§ãã ããã
ãã®èšäºãè±èªåã®èŽè¡ãšå ±æãããå Žåã¯ã翻蚳ãžã®ãªã³ã¯ã䜿çšããŠãã ããïŒAndrey Karpovã PVS-StudioãmacOSã§å©çšå¯èœã«ãªããŸããïŒXNUã«ãŒãã«ã®64ã®åŒ±ç¹ã
èšäºãèªãã§è³ªåããããŸããïŒ
å€ãã®å Žåãèšäºã«ã¯åã質åãå¯ããããŸãã ããã§åçãåéããŸããïŒ PVS-StudioããŒãžã§ã³2015ã«é¢ããèšäºã®èªè
ããã®è³ªåãžã®åç ã ãªã¹ããã芧ãã ããã