@@ -1096,20 +1096,63 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
1096
1096
}
1097
1097
}
1098
1098
1099
- // Special case: you can assign a immutable local variable
1100
- // (e.g., `x = ...`) so long as it has never been initialized
1101
- // before (at this point in the flow).
1102
- if let & Place :: Local ( local) = place_span. 0 {
1103
- if let Mutability :: Not = self . mir . local_decls [ local] . mutability {
1104
- // check for reassignments to immutable local variables
1105
- self . check_if_reassignment_to_immutable_state (
1106
- context,
1107
- local,
1108
- place_span,
1109
- flow_state,
1110
- ) ;
1111
- return ;
1099
+ match place_span. 0 {
1100
+ // Special case: you can assign a immutable local variable
1101
+ // (e.g., `x = ...`) so long as it has never been initialized
1102
+ // before (at this point in the flow).
1103
+ & Place :: Local ( local) => {
1104
+ if let Mutability :: Not = self . mir . local_decls [ local] . mutability {
1105
+ // check for reassignments to immutable local variables
1106
+ self . check_if_reassignment_to_immutable_state (
1107
+ context,
1108
+ local,
1109
+ place_span,
1110
+ flow_state,
1111
+ ) ;
1112
+ return ;
1113
+ }
1112
1114
}
1115
+
1116
+ // FIXME(#21232). For now, error if assigning to a projection from an uninitialized
1117
+ // local variable -- so e.g. doing a.b = 22 when a is not yet initialized is simply an
1118
+ // error. In the future, we could sometimes support this.
1119
+ place @ & Place :: Projection ( _) => {
1120
+ if let Some ( local) = place. base_local ( ) {
1121
+ let mpi = self . move_data . rev_lookup . find_local ( local) ;
1122
+ if flow_state. uninits . contains ( mpi) {
1123
+ let name = self . mir . local_decls [ local] . name . unwrap ( ) ;
1124
+ let msg = match self . describe_place ( place) {
1125
+ Some ( desc) => format ! (
1126
+ "cannot assign to `{}` when `{}` is not initialized" ,
1127
+ desc,
1128
+ name,
1129
+ ) ,
1130
+
1131
+ None => format ! (
1132
+ "use of uninitialized variable `{}" ,
1133
+ name,
1134
+ ) ,
1135
+ } ;
1136
+
1137
+ let mut diag =
1138
+ struct_span_err ! ( self . infcx. tcx. sess, place_span. 1 , E0718 , "{}" , msg) ;
1139
+
1140
+ if let Mutability :: Mut = self . mir . local_decls [ local] . mutability {
1141
+ // Pre-emptively insert local into the used_mut set to avoid any
1142
+ // warnings related to whether the mut declaration is used.
1143
+ self . used_mut . insert ( local) ;
1144
+ } else {
1145
+ diag. span_label ( place_span. 1 , "will also have to be declared `mut`" ) ;
1146
+ }
1147
+
1148
+ diag. buffer ( & mut self . errors_buffer ) ;
1149
+
1150
+ return ;
1151
+ }
1152
+ }
1153
+ }
1154
+
1155
+ _ => { }
1113
1156
}
1114
1157
1115
1158
// Otherwise, use the normal access permission rules.
0 commit comments