TunnelEditorFragment: plug memory leak on listeners
Apparently these don't get GC'd unless they're removed explicitly, because there's a global singleton registry of them. So, introduce a little registry of our own. Reported-by: Samuel Holland <samuel@sholland.org> Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
This commit is contained in:
parent
d615304e83
commit
559add3f71
@ -36,6 +36,8 @@ import com.wireguard.config.Attribute;
|
|||||||
import com.wireguard.config.Config;
|
import com.wireguard.config.Config;
|
||||||
import com.wireguard.config.Peer;
|
import com.wireguard.config.Peer;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collection;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
|
||||||
@ -106,6 +108,7 @@ public class TunnelEditorFragment extends BaseFragment implements AppExclusionLi
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
private final Collection<Object> breakObjectOrientedLayeringHandlerReceivers = new ArrayList<>();
|
||||||
private final Observable.OnPropertyChangedCallback breakObjectOrientedLayeringHandler = new Observable.OnPropertyChangedCallback() {
|
private final Observable.OnPropertyChangedCallback breakObjectOrientedLayeringHandler = new Observable.OnPropertyChangedCallback() {
|
||||||
@Override
|
@Override
|
||||||
public void onPropertyChanged(final Observable sender, final int propertyId) {
|
public void onPropertyChanged(final Observable sender, final int propertyId) {
|
||||||
@ -116,8 +119,11 @@ public class TunnelEditorFragment extends BaseFragment implements AppExclusionLi
|
|||||||
return;
|
return;
|
||||||
if (propertyId == BR.config) {
|
if (propertyId == BR.config) {
|
||||||
config.addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
config.addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
||||||
|
breakObjectOrientedLayeringHandlerReceivers.add(config);
|
||||||
config.getInterfaceSection().addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
config.getInterfaceSection().addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
||||||
|
breakObjectOrientedLayeringHandlerReceivers.add(config.getInterfaceSection());
|
||||||
config.getPeers().addOnListChangedCallback(breakObjectListOrientedLayeringHandler);
|
config.getPeers().addOnListChangedCallback(breakObjectListOrientedLayeringHandler);
|
||||||
|
breakObjectOrientedLayeringHandlerReceivers.add(config.getPeers());
|
||||||
} else if (propertyId == BR.dnses || propertyId == BR.peers)
|
} else if (propertyId == BR.dnses || propertyId == BR.peers)
|
||||||
;
|
;
|
||||||
else
|
else
|
||||||
@ -136,13 +142,21 @@ public class TunnelEditorFragment extends BaseFragment implements AppExclusionLi
|
|||||||
super.onCreateView(inflater, container, savedInstanceState);
|
super.onCreateView(inflater, container, savedInstanceState);
|
||||||
binding = TunnelEditorFragmentBinding.inflate(inflater, container, false);
|
binding = TunnelEditorFragmentBinding.inflate(inflater, container, false);
|
||||||
binding.addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
binding.addOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
||||||
|
breakObjectOrientedLayeringHandlerReceivers.add(binding);
|
||||||
binding.executePendingBindings();
|
binding.executePendingBindings();
|
||||||
return binding.getRoot();
|
return binding.getRoot();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
@Override
|
@Override
|
||||||
public void onDestroyView() {
|
public void onDestroyView() {
|
||||||
binding = null;
|
binding = null;
|
||||||
|
for (final Object o : breakObjectOrientedLayeringHandlerReceivers) {
|
||||||
|
if (o instanceof Observable)
|
||||||
|
((Observable)o).removeOnPropertyChangedCallback(breakObjectOrientedLayeringHandler);
|
||||||
|
else if (o instanceof ObservableList)
|
||||||
|
((ObservableList)o).removeOnListChangedCallback(breakObjectListOrientedLayeringHandler);
|
||||||
|
}
|
||||||
super.onDestroyView();
|
super.onDestroyView();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user