mirror of
				https://github.com/subsurface/subsurface.git
				synced 2025-02-19 22:16:15 +00:00 
			
		
		
		
	Rename event: correctly replace event with new one
I don't like that the event structure includes the variable length array. That really makes it a pain to change the name of an event (on the flip side, freeing events is easier I guess). Anyway, to correctly rename an event we need to actually remove the event from the correct dc and then add a new event with the new name. The previous code was insane (it only worked if the new name was of smaller or equal length, otherwise it had a beautiful buffer overflow). And of course we need to do this both for the current_dive and the displayed_dive. Fixes #616 Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
This commit is contained in:
		
							parent
							
								
									f9b18b9bfb
								
							
						
					
					
						commit
						74616cdddf
					
				
					 3 changed files with 31 additions and 3 deletions
				
			
		
							
								
								
									
										23
									
								
								dive.c
									
										
									
									
									
								
							
							
						
						
									
										23
									
								
								dive.c
									
										
									
									
									
								
							|  | @ -75,6 +75,29 @@ void remove_event(struct event* event) | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | /* since the name is an array as part of the structure (how silly is that?) we
 | ||||||
|  |  * have to actually remove the existing event and replace it with a new one. | ||||||
|  |  * WARNING, WARNING... this may end up freeing event in case that event is indeed | ||||||
|  |  * WARNING, WARNING... part of this divecomputer on this dive! */ | ||||||
|  | void update_event_name(struct dive *d, struct event* event, char *name) | ||||||
|  | { | ||||||
|  | 	if (!d || !event) | ||||||
|  | 		return; | ||||||
|  | 	struct divecomputer *dc = get_dive_dc(d, dc_number); | ||||||
|  | 	if (!dc) | ||||||
|  | 		return; | ||||||
|  | 	struct event **removep = &dc->events; | ||||||
|  | 	struct event *remove; | ||||||
|  | 	while ((*removep)->next && !same_event(*removep, event)) | ||||||
|  | 		removep = &(*removep)->next; | ||||||
|  | 	if (!same_event(*removep, event)) | ||||||
|  | 		return; | ||||||
|  | 	remove = *removep; | ||||||
|  | 	*removep = (*removep)->next; | ||||||
|  | 	add_event(dc, event->time.seconds, event->type, event->flags, event->value, name); | ||||||
|  | 	free(remove); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| /* this returns a pointer to static variable - so use it right away after calling */ | /* this returns a pointer to static variable - so use it right away after calling */ | ||||||
| struct gasmix *get_gasmix_from_event(struct event *ev) | struct gasmix *get_gasmix_from_event(struct event *ev) | ||||||
| { | { | ||||||
|  |  | ||||||
							
								
								
									
										1
									
								
								dive.h
									
										
									
									
									
								
							
							
						
						
									
										1
									
								
								dive.h
									
										
									
									
									
								
							|  | @ -624,6 +624,7 @@ extern void fill_default_cylinder(cylinder_t *cyl); | ||||||
| extern void add_gas_switch_event(struct dive *dive, struct divecomputer *dc, int time, int idx); | extern void add_gas_switch_event(struct dive *dive, struct divecomputer *dc, int time, int idx); | ||||||
| extern void add_event(struct divecomputer *dc, int time, int type, int flags, int value, const char *name); | extern void add_event(struct divecomputer *dc, int time, int type, int flags, int value, const char *name); | ||||||
| extern void remove_event(struct event *event); | extern void remove_event(struct event *event); | ||||||
|  | extern void update_event_name(struct dive *d, struct event* event, char *name); | ||||||
| extern void per_cylinder_mean_depth(struct dive *dive, struct divecomputer *dc, int *mean, int *duration); | extern void per_cylinder_mean_depth(struct dive *dive, struct divecomputer *dc, int *mean, int *duration); | ||||||
| extern int get_cylinder_index(struct dive *dive, struct event *ev); | extern int get_cylinder_index(struct dive *dive, struct event *ev); | ||||||
| extern int nr_cylinders(struct dive *dive); | extern int nr_cylinders(struct dive *dive); | ||||||
|  |  | ||||||
|  | @ -1093,10 +1093,14 @@ void ProfileWidget2::editName() | ||||||
| 			lengthWarning.exec(); | 			lengthWarning.exec(); | ||||||
| 			return; | 			return; | ||||||
| 		} | 		} | ||||||
| 		strcpy(event->name, newName.toUtf8()); | 		// order is important! first update the current dive (by matching the unchanged event),
 | ||||||
| 		remember_event(event->name); | 		// then update the displayed dive (as event is part of the events on displayed dive
 | ||||||
|  | 		// and will be freed as part of changing the name!
 | ||||||
|  | 		update_event_name(current_dive, event, newName.toUtf8().data()); | ||||||
|  | 		update_event_name(&displayed_dive, event, newName.toUtf8().data()); | ||||||
|  | 		mark_divelist_changed(true); | ||||||
|  | 		replot(); | ||||||
| 	} | 	} | ||||||
| 	replot(); |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void ProfileWidget2::disconnectTemporaryConnections() | void ProfileWidget2::disconnectTemporaryConnections() | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue