mirror of
				https://github.com/isar/libmdbx.git
				synced 2025-10-31 15:38:57 +08:00 
			
		
		
		
	lmdb: ITS#7771 fix cursor tracking on fake pages.
node_del shifts nodes around, cursors pointing at fake pages need to have their mc_pg[0] corrected. Includes ITS#7771 more for prev commit.
This commit is contained in:
		
							
								
								
									
										21
									
								
								mdb.c
									
									
									
									
									
								
							
							
						
						
									
										21
									
								
								mdb.c
									
									
									
									
									
								
							| @@ -6673,8 +6673,14 @@ put_sub: | |||||||
| 				for (m2 = mc->mc_txn->mt_cursors[mc->mc_dbi]; m2; m2=m2->mc_next) { | 				for (m2 = mc->mc_txn->mt_cursors[mc->mc_dbi]; m2; m2=m2->mc_next) { | ||||||
| 					if (m2 == mc || m2->mc_snum < mc->mc_snum) continue; | 					if (m2 == mc || m2->mc_snum < mc->mc_snum) continue; | ||||||
| 					if (!(m2->mc_flags & C_INITIALIZED)) continue; | 					if (!(m2->mc_flags & C_INITIALIZED)) continue; | ||||||
| 					if (m2->mc_pg[i] == mp && m2->mc_ki[i] == mc->mc_ki[i]) { | 					if (m2->mc_pg[i] == mp) { | ||||||
|  | 						if (m2->mc_ki[i] == mc->mc_ki[i]) { | ||||||
| 							mdb_xcursor_init2(m2, mx, new_dupdata); | 							mdb_xcursor_init2(m2, mx, new_dupdata); | ||||||
|  | 						} else if (!insert_key) { | ||||||
|  | 							MDB_node *n2 = NODEPTR(mp, m2->mc_ki[i]); | ||||||
|  | 							if (!(n2->mn_flags & F_SUBDATA)) | ||||||
|  | 								m2->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(n2); | ||||||
|  | 						} | ||||||
| 					} | 					} | ||||||
| 				} | 				} | ||||||
| 			} | 			} | ||||||
| @@ -6772,12 +6778,19 @@ mdb_cursor_del(MDB_cursor *mc, unsigned flags) | |||||||
| 					mdb_node_shrink(mp, mc->mc_ki[mc->mc_top]); | 					mdb_node_shrink(mp, mc->mc_ki[mc->mc_top]); | ||||||
| 					leaf = NODEPTR(mp, mc->mc_ki[mc->mc_top]); | 					leaf = NODEPTR(mp, mc->mc_ki[mc->mc_top]); | ||||||
| 					mc->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(leaf); | 					mc->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(leaf); | ||||||
| 					/* fix other sub-DB cursors pointed at this fake page */ | 					/* fix other sub-DB cursors pointed at fake pages on this page */ | ||||||
| 					for (m2 = mc->mc_txn->mt_cursors[mc->mc_dbi]; m2; m2=m2->mc_next) { | 					for (m2 = mc->mc_txn->mt_cursors[mc->mc_dbi]; m2; m2=m2->mc_next) { | ||||||
| 						if (m2 == mc || m2->mc_snum < mc->mc_snum) continue; | 						if (m2 == mc || m2->mc_snum < mc->mc_snum) continue; | ||||||
| 						if (m2->mc_pg[mc->mc_top] == mp && | 						if (!(m2->mc_flags & C_INITIALIZED)) continue; | ||||||
| 							m2->mc_ki[mc->mc_top] == mc->mc_ki[mc->mc_top]) | 						if (m2->mc_pg[mc->mc_top] == mp) { | ||||||
|  | 							if (m2->mc_ki[mc->mc_top] == mc->mc_ki[mc->mc_top]) { | ||||||
| 								m2->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(leaf); | 								m2->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(leaf); | ||||||
|  | 							} else { | ||||||
|  | 								MDB_node *n2 = NODEPTR(mp, m2->mc_ki[mc->mc_top]); | ||||||
|  | 								if (!(n2->mn_flags & F_SUBDATA)) | ||||||
|  | 									m2->mc_xcursor->mx_cursor.mc_pg[0] = NODEDATA(n2); | ||||||
|  | 							} | ||||||
|  | 						} | ||||||
| 					} | 					} | ||||||
| 				} | 				} | ||||||
| 				mc->mc_db->md_entries--; | 				mc->mc_db->md_entries--; | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user