blob: 47d2e247d455c326a60625c0c504fdfc1b747b8d [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.sysds.runtime.privacy.propagation;
import org.apache.sysds.runtime.instructions.cp.ListObject;
import org.apache.sysds.runtime.instructions.cp.ScalarObject;
import org.apache.sysds.runtime.privacy.PrivacyConstraint;
import org.apache.sysds.runtime.privacy.PrivacyConstraint.PrivacyLevel;
import org.apache.sysds.runtime.privacy.PrivacyUtils;
import org.apache.sysds.runtime.privacy.finegrained.DataRange;
import java.util.Map;
public class ListRemovePropagator implements PropagatorMultiReturn {
private final ScalarObject removePosition;
private final PrivacyConstraint removePositionPrivacyConstraint;
private final ListObject list;
private final PrivacyConstraint listPrivacyConstraint;
public ListRemovePropagator(ListObject list, PrivacyConstraint listPrivacyConstraint, ScalarObject removePosition, PrivacyConstraint removePositionPrivacyConstraint){
this.list = list;
this.listPrivacyConstraint = listPrivacyConstraint;
this.removePosition = removePosition;
this.removePositionPrivacyConstraint = removePositionPrivacyConstraint;
}
@Override
public PrivacyConstraint[] propagate() {
PrivacyConstraint output1PrivacyConstraint = new PrivacyConstraint();
PrivacyConstraint output2PrivacyConstraint = new PrivacyConstraint();
propagateGeneralConstraints(output1PrivacyConstraint, output2PrivacyConstraint);
propagateFineGrainedConstraints(output1PrivacyConstraint, output2PrivacyConstraint);
return new PrivacyConstraint[]{output1PrivacyConstraint, output2PrivacyConstraint};
}
private void propagateFineGrainedConstraints(PrivacyConstraint output1PrivacyConstraint, PrivacyConstraint output2PrivacyConstraint){
if ( PrivacyUtils.privacyConstraintFineGrainedActivated(listPrivacyConstraint) ){
propagateFirstHalf(output1PrivacyConstraint);
propagateSecondHalf(output1PrivacyConstraint);
propagateRemovedElement(output2PrivacyConstraint);
}
}
private void propagateFirstHalf(PrivacyConstraint output1PrivacyConstraint){
// The newEndDimension is minus 2 since removePosition is given in 1-index terms whereas the data
// and privacy constraints are 0-index and the privacy constraints are given as closed intervals
long[] newEndDimension = new long[]{removePosition.getLongValue()-2};
Map<DataRange, PrivacyLevel> output1Ranges = listPrivacyConstraint.getFineGrainedPrivacy()
.getPrivacyLevel(new DataRange(new long[]{0}, newEndDimension));
output1Ranges.forEach(
(range, privacyLevel) -> {
long endDim = Long.min(range.getEndDims()[0], removePosition.getLongValue()-2);
DataRange cappedRange = new DataRange(range.getBeginDims(),new long[]{endDim});
output1PrivacyConstraint.getFineGrainedPrivacy().put(cappedRange, privacyLevel);
}
);
}
private void propagateSecondHalf(PrivacyConstraint output1PrivacyConstraint){
Map<DataRange, PrivacyLevel> output2Ranges = listPrivacyConstraint.getFineGrainedPrivacy()
.getPrivacyLevel(new DataRange(new long[]{removePosition.getLongValue()}, new long[]{list.getLength()}));
output2Ranges.forEach(
(range, privacyLevel) -> {
long[] beginDims = new long[]{range.getBeginDims()[0]-1};
long[] endDims = new long[]{range.getEndDims()[0]-1};
output1PrivacyConstraint.getFineGrainedPrivacy().put(new DataRange(beginDims, endDims), privacyLevel);
}
);
}
private void propagateRemovedElement(PrivacyConstraint output2PrivacyConstraint){
if ( output2PrivacyConstraint.getPrivacyLevel() != PrivacyLevel.Private ){
Map<DataRange, PrivacyLevel> elementPrivacy = listPrivacyConstraint.getFineGrainedPrivacy()
.getPrivacyLevelOfElement(new long[]{removePosition.getLongValue()-1});
if ( elementPrivacy.containsValue(PrivacyLevel.Private) )
output2PrivacyConstraint.setPrivacyLevel(PrivacyLevel.Private);
else if ( elementPrivacy.containsValue(PrivacyLevel.PrivateAggregation) )
output2PrivacyConstraint.setPrivacyLevel(PrivacyLevel.PrivateAggregation);
}
}
private void propagateGeneralConstraints(PrivacyConstraint output1PrivacyConstraint, PrivacyConstraint output2PrivacyConstraint){
PrivacyLevel[] inputPrivacyLevels = PrivacyUtils.getGeneralPrivacyLevels(new PrivacyConstraint[]{
listPrivacyConstraint, removePositionPrivacyConstraint
});
PrivacyLevel outputPrivacyLevel = PrivacyPropagator.corePropagation(inputPrivacyLevels, OperatorType.NonAggregate);
output1PrivacyConstraint.setPrivacyLevel(outputPrivacyLevel);
output2PrivacyConstraint.setPrivacyLevel(outputPrivacyLevel);
}
}