(/home/sate/Testcases/c/cve/wireshark-1.2.0/epan/dissectors/packet-ber.c) |
| |
| 1974 | | | int dissect_ber_set(gboolean implicit_tag,asn1_ctx_t *actx, proto_tree *parent_tree, tvbuff_t *tvb, int offset, const ber_sequence_t *set, gint hf_id, gint ett_id) { |
| 1975 | | | gint8 classx; |
| 1976 | | | gboolean pcx, ind = 0, ind_field, imp_tag = FALSE; |
| 1977 | | | gint32 tagx; |
| 1978 | | | guint32 lenx; |
| 1979 | | | proto_tree *tree = parent_tree; |
| 1980 | | | proto_item *item = NULL; |
| 1981 | | | proto_item *cause; |
| 1982 | | | int end_offset, s_offset; |
| 1983 | | | int hoffset; |
| 1984 | | | gint length_remaining; |
| 1985 | | | tvbuff_t *next_tvb; |
| 1986 | | | const ber_sequence_t *cset = NULL; |
| 1987 | | | # define MAX_SET_ELEMENTS 32 |
| 1988 | | | guint32 mandatory_fields = 0; |
| 1989 | | | guint8 set_idx; |
| 1990 | | | gboolean first_pass; |
| 1991 | | | s_offset = offset; |
| 1992 | | | #ifdef DEBUG_BER |
| 1993 | | | { |
| 1994 | | | const char *name; |
| 1995 | | | *hfinfo; |
| 1996 | | | if(hf_id>=0){ |
| 1997 | | | hfinfo = proto_registrar_get_nth(hf_id); |
| 1998 | | | name=hfinfo->name; |
| 1999 | | | } else { |
| 2000 | | | name="unnamed"; |
| 2001 | | | } |
| 2002 | | | if(tvb_length_remaining(tvb,offset)>3){ |
| 2003 | | | printf("SET dissect_ber_set(%s) entered offset:%d len:%d %02x:%02x:%02x\n",name,offset,tvb_length_remaining(tvb,offset),tvb_get_guint8(tvb,offset),tvb_get_guint8(tvb,offset+1),tvb_get_guint8(tvb,offset+2)); |
| 2004 | | | }else{ |
| 2005 | | | printf("SET dissect_ber_set(%s) entered\n",name); |
| 2006 | | | } |
| 2007 | | | } |
| 2008 | | | #endif |
| 2009 | | | |
| 2010 | | | if(!implicit_tag){ |
Event 1:
Taking false branch. implicit_tag evaluates to true.
hide
|
|
| 2011 | | | hoffset = offset; |
| 2012 | | | |
| 2013 | | | offset = dissect_ber_identifier(actx->pinfo, tree, tvb, offset, &classx, &pcx, &tagx); |
| 2014 | | | offset = dissect_ber_length(actx->pinfo, tree, tvb, offset, &lenx, &ind); |
| 2015 | | | if(ind){ |
| 2016 | | | |
| 2017 | | | |
| 2018 | | | end_offset = offset + lenx -2; |
| 2019 | | | } else { |
| 2020 | | | end_offset = offset + lenx; |
| 2021 | | | } |
| 2022 | | | |
| 2023 | | | |
| 2024 | | | if ((classx!=BER_CLASS_APP)&&(classx!=BER_CLASS_PRI)) |
| 2025 | | | if ((!pcx) |
| 2026 | | | ||(!implicit_tag&&((classx!=BER_CLASS_UNI) |
| 2027 | | | ||(tagx!=BER_UNI_TAG_SET)))) { |
| 2028 | | | tvb_ensure_bytes_exist(tvb, hoffset, 2); |
| 2029 | | | cause = proto_tree_add_text(tree, tvb, offset, lenx, "BER Error: SET expected but class:%s(%d) %s tag:%d was found", val_to_str(classx,ber_class_codes,"Unknown"), classx, pcx ? ber_pc_codes_short.true_string : ber_pc_codes_short.false_string, tagx); |
| 2030 | | | proto_item_set_expert_flags(cause, PI_MALFORMED, PI_WARN); |
| 2031 | | | expert_add_info_format(actx->pinfo, cause, PI_MALFORMED, PI_WARN, "BER Error: SET expected"); |
| 2032 | | | if (decode_unexpected) { |
| 2033 | | | proto_tree *unknown_tree = proto_item_add_subtree(cause, ett_ber_unknown); |
| 2034 | | | dissect_unknown_ber(actx->pinfo, tvb, hoffset, unknown_tree); |
| 2035 | | | } |
| 2036 | | | return end_offset; |
| 2037 | | | } |
| 2038 | | | } else { |
| 2039 | | | |
| 2040 | | | lenx=tvb_length_remaining(tvb,offset); |
| 2041 | | | end_offset=offset+lenx; |
| 2042 | | | } |
| 2043 | | | |
| 2044 | | | |
| 2045 | | | if (hf_id >= 0) { |
Event 2:
Skipping " if". hf_id >= 0 evaluates to false.
hide
|
|
| 2046 | | | if(parent_tree){ |
| 2047 | | | item = proto_tree_add_item(parent_tree, hf_id, tvb, offset, lenx, FALSE); |
| 2048 | | | tree = proto_item_add_subtree(item, ett_id); |
| 2049 | | | } |
| 2050 | | | } |
| 2051 | | | |
| 2052 | | | |
| 2053 | | | |
| 2054 | | | for(set_idx = 0; (cset=&set[set_idx])->func && (set_idx < MAX_SET_ELEMENTS); set_idx++) { |
Event 3:
set_idx is set to 0.
hide
Event 4:
cset is set to set. See related event 3.
hide
Event 5:
Leaving loop. (cset = &set[set_idx])->func evaluates to false.
hide
Event 6:
Considering the case where cset->func is equal to 0 so set->func must have been equal to 0. See related event 4.
hide
|
|
| 2055 | | | |
| 2056 | | | if(!(cset->flags & BER_FLAGS_OPTIONAL)) |
| 2057 | | | mandatory_fields |= 1 << set_idx; |
| 2058 | | | |
| 2059 | | | } |
| 2060 | | | |
| 2061 | | | |
| 2062 | | | while (offset < end_offset){ |
Event 7:
Entering loop body. offset < end_offset evaluates to true.
hide
|
|
| 2063 | | | gint8 class; |
| 2064 | | | gboolean pc; |
| 2065 | | | gint32 tag; |
| 2066 | | | guint32 len; |
| 2067 | | | int eoffset, count; |
| 2068 | | | |
| 2069 | | | |
| 2070 | | | |
| 2071 | | | |
| 2072 | [+] | | if((tvb_get_guint8(tvb, offset)==0)&&(tvb_get_guint8(tvb, offset+1)==0)){ |
 |
| 2073 | | | if(show_internal_ber_fields){ |
| 2074 | | | proto_tree_add_text(tree, tvb, s_offset, offset+2, "SEQ EOC"); |
| 2075 | | | } |
| 2076 | | | return end_offset; |
| 2077 | | | } |
| 2078 | | | |
| 2079 | | | hoffset = offset; |
| 2080 | | | |
| 2081 | | | offset = get_ber_identifier(tvb, offset, &class, &pc, &tag); |
| 2082 | | | offset = get_ber_length(tvb, offset, &len, &ind_field); |
| 2083 | | | eoffset = offset + len; |
| 2084 | | | |
| 2085 | | | |
| 2086 | | | |
| 2087 | | | |
| 2088 | | | |
| 2089 | | | |
| 2090 | | | |
| 2091 | | | |
| 2092 | | | for(first_pass=TRUE, cset = set, set_idx = 0; cset->func || first_pass; cset++, set_idx++) { |
Event 13:
Entering loop body. !0 evaluates to true.
hide
Event 15:
Continuing from loop body. Entering loop body. cset->func evaluates to true.
hide
|
|
| 2093 | | | |
| 2094 | | | |
| 2095 | | | if(!cset->func) { |
Event 16:
Skipping " if". cset->func evaluates to true.
hide
Event 19:
Taking true branch. cset->func evaluates to false.
hide
|
|
| 2096 | | | first_pass = FALSE; |
| 2097 | | | |
| 2098 | | | cset=set; |
Event 20:
cset is set to set. - Dereferenced later, causing the null pointer dereference.
hide
|
|
| 2099 | | | set_idx = 0; |
| 2100 | | | } |
| 2101 | | | |
| 2102 | | | if((first_pass && ((cset->class==class) && (cset->tag==tag))) || |
Event 17:
Skipping " if". - first_pass evaluates to true.
- cset->class == class evaluates to false.
- first_pass evaluates to true.
hide
|
|
| 2103 | | | (!first_pass && ((cset->class== BER_CLASS_ANY) && (cset->tag == -1))) ) |
| 2104 | | | { |
| 2105 | | | |
| 2106 | | | if (!(cset->flags & BER_FLAGS_NOOWNTAG) ) { |
Event 22:
Taking false branch. cset->flags & 4 evaluates to true.
hide
|
|
| 2107 | | | |
| 2108 | | | hoffset = dissect_ber_identifier(actx->pinfo, tree, tvb, hoffset, NULL, NULL, NULL); |
| 2109 | | | hoffset = dissect_ber_length(actx->pinfo, tree, tvb, hoffset, NULL, NULL); |
| 2110 | | | length_remaining=tvb_length_remaining(tvb, hoffset); |
| 2111 | | | if (length_remaining>eoffset-hoffset-(2*ind_field)) |
| 2112 | | | length_remaining=eoffset-hoffset-(2*ind_field); |
| 2113 | | | next_tvb = tvb_new_subset(tvb, hoffset, length_remaining, eoffset-hoffset-(2*ind_field)); |
| 2114 | | | } |
| 2115 | | | else { |
| 2116 | | | length_remaining=tvb_length_remaining(tvb, hoffset); |
| 2117 | | | if (length_remaining>eoffset-hoffset) |
Event 23:
Taking true branch. length_remaining > eoffset - hoffset evaluates to true.
hide
|
|
| 2118 | | | length_remaining=eoffset-hoffset; |
| 2119 | [+] | | next_tvb = tvb_new_subset(tvb, hoffset, length_remaining, eoffset-hoffset); |
 |
| 2120 | | | } |
| 2121 | | | |
| 2122 | | | |
| 2123 | | | |
| 2124 | | | |
| 2125 | | | |
| 2126 | | | |
| 2127 | | | |
| 2128 | | | |
| 2129 | | | |
| 2130 2140 |  | | [ Lines 2130 to 2140 omitted. ] |
| 2141 | | | } else { |
| 2142 | | | name="unnamed"; |
| 2143 | | | } |
| 2144 | | | if(tvb_length_remaining(next_tvb,0)>3){ |
| 2145 | | | printf("SET dissect_ber_set(%s) calling subdissector offset:%d len:%d %02x:%02x:%02x\n",name,offset,tvb_length_remaining(next_tvb,0),tvb_get_guint8(next_tvb,0),tvb_get_guint8(next_tvb,1),tvb_get_guint8(next_tvb,2)); |
| 2146 | | | }else{ |
| 2147 | | | printf("SET dissect_ber_set(%s) calling subdissector\n",name); |
| 2148 | | | } |
| 2149 | | | } |
| 2150 | | | #endif |
| 2151 | | | if (next_tvb == NULL) { |
Event 26:
Skipping " if". next_tvb == (void *)0 evaluates to false.
hide
|
|
| 2152 | | | |
| 2153 | | | THROW(ReportedBoundsError);
x /home/sate/Testcases/c/cve/wireshark-1.2.0/epan/exceptions.h |
| |
223 | #define THROW(x) \ |
224 | except_throw(XCEPT_GROUP_WIRESHARK, (x), NULL) |
| |
|
| 2154 | | | } |
| 2155 | | | imp_tag = FALSE; |
| 2156 | | | if ((cset->flags & BER_FLAGS_IMPLTAG)) |
Event 27:
Skipping " if". cset->flags & 2 evaluates to false.
hide
|
|
| 2157 | | | imp_tag = TRUE; |
| 2158 | | | count=cset->func(imp_tag, next_tvb, 0, actx, tree, *cset->p_id); |
Null Pointer Dereference
cset->func is dereferenced here, but it is NULL. - cset->func evaluates to set->func, which must be equal to 0.
The issue can occur if the highlighted code executes. See related events 6 and 20. Show: All events | Only primary events |
|
| 2159 | | | |
| 2160 | | | |
| 2161 | | | |
| 2162 | | | if(count || (first_pass && (len == 0 || (ind_field == 1 && len == 2)))) { |
| |