Exemple #1
0
    def _privacy_accounting(self, q, iters, eps, delta=0.001):
        """Compute sigma if necessary and use it to compute eps"""

        acc = accountant.GaussianMomentsAccountant(
            verbose=False,
            moment_orders=128,  # for eps=0.1
            seed=np.random.get_state()[1][0])
        if eps > 0:
            self.sigma = acc.compute_sigma2(eps=eps,
                                            delta=delta,
                                            q=q,
                                            iters=iters)
            print("Sigma: %g" % self.sigma)
        if self.sigma > 0:
            acc.accumulate_privacy_spending(sigma=self.sigma,
                                            q=q,
                                            iters=iters,
                                            reset=True)
            measured_eps = acc.get_privacy_spent(target_deltas=[delta])[0][0]
            if abs(measured_eps - eps) > eps:
                raise (ArithmeticError(
                    "Target eps=%g whereas measured eps=%g" %
                    (eps, measured_eps)))
            print("Eps: %g" %
                  acc.get_privacy_spent(target_deltas=[delta])[0][0])
            print("Delta: %g" % delta)
Exemple #2
0
def GAN_solvers(D_loss,
                G_loss,
                learning_rate,
                batch_size,
                total_examples,
                l2norm_bound,
                batches_per_lot,
                sigma,
                dp=False):
    """
    Optimizers
    """
    discriminator_vars = [
        v for v in tf.trainable_variables()
        if v.name.startswith('discriminator')
    ]
    generator_vars = [
        v for v in tf.trainable_variables() if v.name.startswith('generator')
    ]
    if dp:
        print('Using differentially private SGD to train discriminator!')
        eps = tf.placeholder(tf.float32)
        delta = tf.placeholder(tf.float32)
        priv_accountant = accountant.GaussianMomentsAccountant(total_examples)
        clip = True
        l2norm_bound = l2norm_bound / batch_size
        batches_per_lot = 1
        gaussian_sanitizer = sanitizer.AmortizedGaussianSanitizer(
            priv_accountant, [l2norm_bound, clip])

        # the trick is that we need to calculate the gradient with respect to
        # each example in the batch, during the DP SGD step
        D_solver = dp_optimizer.DPGradientDescentOptimizer(
            learning_rate, [eps, delta],
            sanitizer=gaussian_sanitizer,
            sigma=sigma,
            batches_per_lot=batches_per_lot).minimize(
                D_loss, var_list=discriminator_vars)
    else:
        D_loss_mean_over_batch = tf.reduce_mean(D_loss)
        D_solver = tf.train.GradientDescentOptimizer(
            learning_rate=learning_rate).minimize(D_loss_mean_over_batch,
                                                  var_list=discriminator_vars)
        priv_accountant = None
    G_loss_mean_over_batch = tf.reduce_mean(G_loss)
    G_solver = tf.train.AdamOptimizer().minimize(G_loss_mean_over_batch,
                                                 var_list=generator_vars)
    return D_solver, G_solver, priv_accountant
Exemple #3
0
def train():
  """Train CIFAR-10 for a number of steps."""
  with tf.Graph().as_default():
    global_step = tf.Variable(0, trainable=False)

    # Get images and labels for CIFAR-10.
    images, labels = cifar10.distorted_inputs()
    labels = tf.one_hot(labels, 10)

    # Build a Graph that computes the logits predictions from the
    # inference model.
    #logits = inference(images)

    with tf.variable_scope('conv1') as scope:
        kernel1 = _variable_with_weight_decay('weights',
                                          shape=[3, 3, 3, 128],
                                          stddev=5e-2,
                                          wd=None)
        conv = tf.nn.conv2d(images, kernel1, [1, 2, 2, 1], padding='SAME')
        #conv = tf.nn.dropout(conv, 0.9)
        biases1 = cifar10._variable_on_cpu('biases', [128], tf.constant_initializer(0.0))
        pre_activation = tf.nn.bias_add(conv, biases1)
        conv1 = tf.nn.relu(pre_activation, name = scope.name)
        cifar10._activation_summary(conv1)
                                              
    norm1 = tf.contrib.layers.batch_norm(conv1, scale=True, is_training=True, updates_collections=None)
        
    # conv2
    with tf.variable_scope('conv2') as scope:
        kernel2 = _variable_with_weight_decay('weights',
                                            shape=[5, 5, 128, 128],
                                            stddev=5e-2,
                                            wd=None)
        conv = tf.nn.conv2d(norm1, kernel2, [1, 1, 1, 1], padding='SAME')
        biases2 = cifar10._variable_on_cpu('biases', [128], tf.constant_initializer(0.1))
        pre_activation = tf.nn.bias_add(conv, biases2)
        conv2 = tf.nn.relu(pre_activation, name = scope.name)
        #conv2 = tf.nn.dropout(conv2, 0.9)
        cifar10._activation_summary(conv2)
                                                                              
    # concat conv2 with norm1 to increase the number of features, this step does not affect the privacy preserving guarantee
    current = tf.concat((conv2, norm1), axis=3)
    # norm2
    norm2 = tf.contrib.layers.batch_norm(current, scale=True, is_training=True, updates_collections=None)
        
    # conv3
    with tf.variable_scope('conv3') as scope:
        kernel3 = _variable_with_weight_decay('weights',
                                    shape=[5, 5, 256, 256],
                                    stddev=5e-2,
                                    wd=None)
        conv = tf.nn.conv2d(norm2, kernel3, [1, 1, 1, 1], padding='SAME')
        biases3 = cifar10._variable_on_cpu('biases', [256], tf.constant_initializer(0.1))
        pre_activation = tf.nn.bias_add(conv, biases3)
        conv3 = tf.nn.relu(pre_activation, name = scope.name)
        #conv3 = tf.nn.dropout(conv3, 0.9)
        cifar10._activation_summary(conv3)
                                                                                                                  
    # norm3
    norm3 = tf.contrib.layers.batch_norm(conv3, scale=True, is_training=True, updates_collections=None)
    #pool3, row_pooling_sequence, col_pooling_sequence = tf.nn.fractional_max_pool(norm3, pooling_ratio=[1.0, 2.0, 2.0, 1.0])
    pool3 = avg_pool(norm3, 2)
                                                                                                                          
    # local4
    with tf.variable_scope('local4') as scope:
        weights1 = cifar10._variable_with_weight_decay('weights', shape=[5*5*256, hk],
                                    stddev=0.04, wd=None)
        biases4 = cifar10._variable_on_cpu('biases', [hk], tf.constant_initializer(0.1))
        h_pool2_flat = tf.reshape(pool3, [-1, 5*5*256]);
        z2 = tf.add(tf.matmul(h_pool2_flat, weights1), biases4, name=scope.name)
        #Applying normalization for the flat connected layer h_fc1#
        batch_mean2, batch_var2 = tf.nn.moments(z2,[0])
        scale2 = tf.Variable(tf.ones([hk]))
        beta2 = tf.Variable(tf.zeros([hk]))
        BN_norm = tf.nn.batch_normalization(z2,batch_mean2,batch_var2,beta2,scale2,1e-3)
        ###
        local4 = max_out(BN_norm, hk)
        cifar10._activation_summary(local4)
    # linear layer(WX + b),
    # We don't apply softmax here because
    # tf.nn.sparse_softmax_cross_entropy_with_logits accepts the unscaled logits
    # and performs the softmax internally for efficiency.
    weights2 = cifar10._variable_with_weight_decay('weights', [hk, 10],
                                            stddev=1/(hk*1.0), wd=0.0)
    biases5 = cifar10._variable_on_cpu('biases', [10], tf.constant_initializer(0.0))
    logits = tf.add(tf.matmul(local4, weights2), biases5, name=scope.name)
    cifar10._activation_summary(logits)

    # Calculate loss. Apply Taylor Expansion for the output layer
    #loss = cifar10.loss(logits, labels)

    # Calculate the average cross entropy loss across the batch.
    labels = tf.cast(labels, tf.int64)
    cross_entropy = tf.nn.softmax_cross_entropy_with_logits(
                    labels=labels, logits=logits, name='cross_entropy_per_example')
    loss = tf.reduce_mean(cross_entropy, name='cross_entropy')

    opt = tf.train.GradientDescentOptimizer(lr)

    gw_K1 = tf.gradients(loss, kernel1)[0]
    gb1 = tf.gradients(loss, biases1)[0]

    gw_K2 = tf.gradients(loss, kernel2)[0]
    gb2 = tf.gradients(loss, biases2)[0]
    
    gw_K3 = tf.gradients(loss, kernel3)[0]
    gb3 = tf.gradients(loss, biases3)[0]

    gw_W1 = tf.gradients(loss, weights1)[0]
    gb4 = tf.gradients(loss, biases4)[0]
    
    gw_W2 = tf.gradients(loss, weights2)[0]
    gb5 = tf.gradients(loss, biases5)[0]

    #clip gradient
    gw_K1 = tf.clip_by_norm(gw_K1,clip_bound)
    gw_K2 = tf.clip_by_norm(gw_K2,clip_bound)
    gw_K3 = tf.clip_by_norm(gw_K3,clip_bound)
    gw_W1 = tf.clip_by_norm(gw_W1,clip_bound)
    gw_W2 = tf.clip_by_norm(gw_W2,clip_bound)

    #perturb
    gw_K1 += tf.random_normal(shape=tf.shape(gw_K1), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gw_K2 += tf.random_normal(shape=tf.shape(gw_K2), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gw_K3 += tf.random_normal(shape=tf.shape(gw_K3), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gw_W1 += tf.random_normal(shape=tf.shape(gw_W1), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gw_W2 += tf.random_normal(shape=tf.shape(gw_W2), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gb1 += tf.random_normal(shape=tf.shape(gb1), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gb2 += tf.random_normal(shape=tf.shape(gb2), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gb3 += tf.random_normal(shape=tf.shape(gb3), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gb4 += tf.random_normal(shape=tf.shape(gb4), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    gb5 += tf.random_normal(shape=tf.shape(gb5), mean=0.0, stddev = sigma * (sensitivity**2), dtype=tf.float32)
    
    # apply gradients and keep tracking moving average of the parameters
    apply_gradient_op = opt.apply_gradients([(gw_K1,kernel1),(gb1,biases1),(gw_K2,kernel2),(gb2,biases2),(gw_K3,kernel3),(gb3,biases3),(gw_W1,weights1),(gb4,biases4),(gw_W2,weights2),(gb5,biases5)], global_step=global_step);
    variable_averages = tf.train.ExponentialMovingAverage(MOVING_AVERAGE_DECAY, global_step)
    variables_averages_op = variable_averages.apply(tf.trainable_variables())
    with tf.control_dependencies([apply_gradient_op, variables_averages_op]):
        train_op = tf.no_op(name='train')

    # Create a saver.
    saver = tf.train.Saver(tf.all_variables())
    
    # Privacy accountant
    priv_accountant = accountant.GaussianMomentsAccountant(D)
    privacy_accum_op = priv_accountant.accumulate_privacy_spending([None, None], sigma, batch_size)
    
    # Build the summary operation based on the TF collection of Summaries.
    summary_op = tf.summary.merge_all()

    # Build an initialization operation to run below.
    init = tf.initialize_all_variables()

    # Start running operations on the Graph.
    sess = tf.Session(config=tf.ConfigProto(log_device_placement=False))
    sess.run(init)

    # Start the queue runners.
    tf.train.start_queue_runners(sess=sess)

    summary_writer = tf.summary.FileWriter(os.getcwd() + '/tmp/cifar10_train', sess.graph)
    
    # load the most recent models
    _global_step = 0
    ckpt = tf.train.get_checkpoint_state(FLAGS.checkpoint_dir)
    if ckpt and ckpt.model_checkpoint_path:
        print(ckpt.model_checkpoint_path);
        saver.restore(sess, ckpt.model_checkpoint_path)
        _global_step = int(ckpt.model_checkpoint_path.split('/')[-1].split('-')[-1])
    else:
        print('No checkpoint file found')
    
    T = int(int(math.ceil(D/batch_size))*epochs + 1) # number of steps
    step_for_epoch = int(math.ceil(D/batch_size)); #number of steps for one epoch
    for step in xrange(_global_step, _global_step + T):
      start_time = time.time()
      _, loss_value = sess.run([train_op, loss])
      duration = time.time() - start_time

      assert not np.isnan(loss_value), 'Model diverged with loss = NaN'
      
      # report the result periodically
      if step % (5*step_for_epoch) == 0:
        num_examples_per_step = batch_size
        examples_per_sec = num_examples_per_step / duration
        sec_per_batch = float(duration)

        format_str = ('%s: step %d, loss = %.2f (%.1f examples/sec; %.3f '
                      'sec/batch)')
        print (format_str % (datetime.now(), step, loss_value,
                             examples_per_sec, sec_per_batch))

      if step % (5*step_for_epoch) == 0:
        summary_str = sess.run(summary_op)
        summary_writer.add_summary(summary_str, step)

      # Save the model checkpoint periodically.
      if step % (5*step_for_epoch) == 0 and (step > _global_step):
        checkpoint_path = os.path.join(os.getcwd() + '/tmp/cifar10_train', 'model.ckpt')
        saver.save(sess, checkpoint_path, global_step=step);
        sess.run([privacy_accum_op])
        spent_eps_deltas = priv_accountant.get_privacy_spent(sess, target_eps=target_eps)
        print(step, spent_eps_deltas)

      sess.run([privacy_accum_op])
      spent_eps_deltas = priv_accountant.get_privacy_spent(sess, target_eps=target_eps)
      _break = False;
      for _eps, _delta in spent_eps_deltas:
        if _delta >= delta:
            _break = True;
            break;
      if _break == True:
        break;
Exemple #4
0
def train(cifar10_data, logfile):
    """Train CIFAR-10 for a number of steps."""
    logfile.write("fgsm_eps \t %g, epsilon \t %d \n" %
                  (fgsm_eps, target_eps[0]))
    with tf.Graph().as_default():
        global_step = tf.Variable(0, trainable=False)

        # Parameters Declarification
        #with tf.variable_scope('conv1') as scope:
        kernel1 = _variable_with_weight_decay(
            'kernel1',
            shape=[3, 3, 3, 128],
            stddev=np.sqrt(2.0 / (5 * 5 * 256)) / math.ceil(5 / 2),
            wd=0.0)
        biases1 = cifar10._variable_on_cpu('biases1', [128],
                                           tf.constant_initializer(0.0))
        #with tf.variable_scope('conv2') as scope:
        kernel2 = _variable_with_weight_decay(
            'kernel2',
            shape=[5, 5, 128, 128],
            stddev=np.sqrt(2.0 / (5 * 5 * 256)) / math.ceil(5 / 2),
            wd=0.0)
        biases2 = cifar10._variable_on_cpu('biases2', [128],
                                           tf.constant_initializer(0.1))
        #with tf.variable_scope('conv3') as scope:
        kernel3 = _variable_with_weight_decay(
            'kernel3',
            shape=[5, 5, 256, 256],
            stddev=np.sqrt(2.0 / (5 * 5 * 256)) / math.ceil(5 / 2),
            wd=0.0)
        biases3 = cifar10._variable_on_cpu('biases3', [256],
                                           tf.constant_initializer(0.1))
        #with tf.variable_scope('local4') as scope:
        kernel4 = cifar10._variable_with_weight_decay(
            'kernel4',
            shape=[int(image_size / 4)**2 * 256, hk],
            stddev=0.04,
            wd=0.004)
        biases4 = cifar10._variable_on_cpu('biases4', [hk],
                                           tf.constant_initializer(0.1))
        #with tf.variable_scope('local5') as scope:
        kernel5 = cifar10._variable_with_weight_decay(
            'kernel5', [hk, 10],
            stddev=np.sqrt(2.0 /
                           (int(image_size / 4)**2 * 256)) / math.ceil(5 / 2),
            wd=0.0)
        biases5 = cifar10._variable_on_cpu('biases5', [10],
                                           tf.constant_initializer(0.1))

        scale2 = tf.Variable(tf.ones([hk]))
        beta2 = tf.Variable(tf.zeros([hk]))

        params = [
            kernel1, biases1, kernel2, biases2, kernel3, biases3, kernel4,
            biases4, kernel5, biases5, scale2, beta2
        ]
        ########

        # Build a Graph that computes the logits predictions from the
        # inference model.
        shape = kernel1.get_shape().as_list()
        w_t = tf.reshape(kernel1, [-1, shape[-1]])
        w = tf.transpose(w_t)
        sing_vals = tf.svd(w, compute_uv=False)
        sensitivityW = tf.reduce_max(sing_vals)
        dp_delta = 0.05
        #dp_mult = attack_norm_bound * math.sqrt(2 * math.log(1.25 / dp_delta)) / dp_epsilon
        noise = tf.placeholder(tf.float32, [None, 28, 28, 32])

        dp_mult = attack_norm_bound * math.sqrt(
            2 * math.log(1.25 / dp_delta)) / dp_epsilon
        noise = tf.placeholder(tf.float32, [None, 14, 14, 128])
        sigma = tf.placeholder(tf.float32)
        x = tf.placeholder(tf.float32, [None, image_size, image_size, 3])
        #y_conv, h_conv1 = inference(x, params, dp_mult**2 * noise);
        y_conv, h_conv1 = inference(x, params, attack_norm_bound * noise)
        softmax_y_conv = tf.nn.softmax(y_conv)
        y_ = tf.placeholder(tf.float32, [None, 10])

        #logits = inference(images)

        # Calculate loss. Apply Taylor Expansion for the output layer
        loss = cifar10.lossDPSGD(y_conv, y_)

        # noise redistribution #
        grad, = tf.gradients(loss, h_conv1)
        normalized_grad = tf.sign(grad)
        normalized_grad = tf.stop_gradient(normalized_grad)
        normalized_grad_r = tf.abs(tf.reduce_mean(normalized_grad,
                                                  axis=(0)))**2
        sum_r = tf.reduce_sum(normalized_grad_r,
                              axis=(0, 1, 2),
                              keepdims=False)
        normalized_grad_r = 14 * 14 * 128 * normalized_grad_r / sum_r
        print(normalized_grad_r)

        shape_grad = normalized_grad_r.get_shape().as_list()
        grad_t = tf.reshape(normalized_grad_r, [-1, shape_grad[-1]])
        g = tf.transpose(grad_t)
        sing_g_vals = tf.svd(g, compute_uv=False)
        sensitivity_2 = tf.reduce_max(sing_g_vals)
        ########################

        opt = tf.train.GradientDescentOptimizer(lr)

        gw_K1 = tf.gradients(loss, kernel1)[0]
        gb1 = tf.gradients(loss, biases1)[0]

        gw_K2 = tf.gradients(loss, kernel2)[0]
        gb2 = tf.gradients(loss, biases2)[0]

        gw_K3 = tf.gradients(loss, kernel3)[0]
        gb3 = tf.gradients(loss, biases3)[0]

        gw_K4 = tf.gradients(loss, kernel4)[0]
        gb4 = tf.gradients(loss, biases4)[0]

        gw_K5 = tf.gradients(loss, kernel5)[0]
        gb5 = tf.gradients(loss, biases5)[0]

        #clip gradient
        gw_K1 = tf.clip_by_norm(gw_K1, clip_bound)
        gw_K2 = tf.clip_by_norm(gw_K2, clip_bound)
        gw_K3 = tf.clip_by_norm(gw_K3, clip_bound)
        gw_K4 = tf.clip_by_norm(gw_K4, clip_bound)
        gw_K5 = tf.clip_by_norm(gw_K5, clip_bound)

        #perturb
        gw_K1 += tf.random_normal(shape=tf.shape(gw_K1),
                                  mean=0.0,
                                  stddev=(sigma * sensitivity),
                                  dtype=tf.float32) / batch_size
        gw_K2 += tf.random_normal(shape=tf.shape(gw_K2),
                                  mean=0.0,
                                  stddev=(sigma * sensitivity),
                                  dtype=tf.float32) / batch_size
        gw_K3 += tf.random_normal(shape=tf.shape(gw_K3),
                                  mean=0.0,
                                  stddev=(sigma * sensitivity),
                                  dtype=tf.float32) / batch_size
        gw_K4 += tf.random_normal(shape=tf.shape(gw_K4),
                                  mean=0.0,
                                  stddev=(sigma * sensitivity),
                                  dtype=tf.float32) / batch_size
        gw_K5 += tf.random_normal(shape=tf.shape(gw_K5),
                                  mean=0.0,
                                  stddev=(sigma * sensitivity),
                                  dtype=tf.float32) / batch_size
        gb1 += tf.random_normal(shape=tf.shape(gb1),
                                mean=0.0,
                                stddev=(sigma * sensitivity),
                                dtype=tf.float32) / batch_size
        gb2 += tf.random_normal(shape=tf.shape(gb2),
                                mean=0.0,
                                stddev=(sigma * sensitivity),
                                dtype=tf.float32) / batch_size
        gb3 += tf.random_normal(shape=tf.shape(gb3),
                                mean=0.0,
                                stddev=(sigma * sensitivity),
                                dtype=tf.float32) / batch_size
        gb4 += tf.random_normal(shape=tf.shape(gb4),
                                mean=0.0,
                                stddev=(sigma * sensitivity),
                                dtype=tf.float32) / batch_size
        gb5 += tf.random_normal(shape=tf.shape(gb5),
                                mean=0.0,
                                stddev=(sigma * sensitivity),
                                dtype=tf.float32) / batch_size

        # apply gradients and keep tracking moving average of the parameters
        apply_gradient_op = opt.apply_gradients([(gw_K1, kernel1),
                                                 (gb1, biases1),
                                                 (gw_K2, kernel2),
                                                 (gb2, biases2),
                                                 (gw_K3, kernel3),
                                                 (gb3, biases3),
                                                 (gw_K4, kernel4),
                                                 (gb4, biases4),
                                                 (gw_K5, kernel5),
                                                 (gb5, biases5)],
                                                global_step=global_step)
        variable_averages = tf.train.ExponentialMovingAverage(
            MOVING_AVERAGE_DECAY, global_step)
        variables_averages_op = variable_averages.apply(
            tf.trainable_variables())
        with tf.control_dependencies(
            [apply_gradient_op, variables_averages_op]):
            train_op = tf.no_op(name='train')

        # Build a Graph that trains the model with one batch of examples and
        # updates the model parameters.
        #train_op = cifar10.trainDPSGD(loss, global_step, clip_bound, sigma, sensitivity)

        sess = tf.Session(config=tf.ConfigProto(log_device_placement=False))

        attack_switch = {
            'fgsm': True,
            'ifgsm': True,
            'deepfool': False,
            'mim': True,
            'spsa': False,
            'cwl2': False,
            'madry': True,
            'stm': False
        }

        ch_model_probs = CustomCallableModelWrapper(
            callable_fn=inference_test_input_probs,
            output_layer='probs',
            params=params,
            image_size=image_size)

        # define each attack method's tensor
        attack_tensor_dict = {}
        # FastGradientMethod
        if attack_switch['fgsm']:
            print('creating attack tensor of FastGradientMethod')
            fgsm_obj = FastGradientMethod(model=ch_model_probs, sess=sess)
            #x_adv_test_fgsm = fgsm_obj.generate(x=x, eps=fgsm_eps, clip_min=-1.0, clip_max=1.0, ord=2) # testing now
            x_adv_test_fgsm = fgsm_obj.generate(x=x,
                                                eps=fgsm_eps,
                                                clip_min=-1.0,
                                                clip_max=1.0)  # testing now
            attack_tensor_dict['fgsm'] = x_adv_test_fgsm

        # Iterative FGSM (BasicIterativeMethod/ProjectedGradientMethod with no random init)
        # default: eps_iter=0.05, nb_iter=10
        if attack_switch['ifgsm']:
            print('creating attack tensor of BasicIterativeMethod')
            ifgsm_obj = BasicIterativeMethod(model=ch_model_probs, sess=sess)
            #x_adv_test_ifgsm = ifgsm_obj.generate(x=x, eps=fgsm_eps, eps_iter=fgsm_eps/10, nb_iter=10, clip_min=-1.0, clip_max=1.0, ord=2)
            x_adv_test_ifgsm = ifgsm_obj.generate(x=x,
                                                  eps=fgsm_eps,
                                                  eps_iter=fgsm_eps / 3,
                                                  nb_iter=3,
                                                  clip_min=-1.0,
                                                  clip_max=1.0)
            attack_tensor_dict['ifgsm'] = x_adv_test_ifgsm

        # MomentumIterativeMethod
        # default: eps_iter=0.06, nb_iter=10
        if attack_switch['mim']:
            print('creating attack tensor of MomentumIterativeMethod')
            mim_obj = MomentumIterativeMethod(model=ch_model_probs, sess=sess)
            #x_adv_test_mim = mim_obj.generate(x=x, eps=fgsm_eps, eps_iter=fgsm_eps/10, nb_iter=10, decay_factor=1.0, clip_min=-1.0, clip_max=1.0, ord=2)
            x_adv_test_mim = mim_obj.generate(x=x,
                                              eps=fgsm_eps,
                                              eps_iter=fgsm_eps / 3,
                                              nb_iter=3,
                                              decay_factor=1.0,
                                              clip_min=-1.0,
                                              clip_max=1.0)
            attack_tensor_dict['mim'] = x_adv_test_mim

        # MadryEtAl (Projected Grdient with random init, same as rand+fgsm)
        # default: eps_iter=0.01, nb_iter=40
        if attack_switch['madry']:
            print('creating attack tensor of MadryEtAl')
            madry_obj = MadryEtAl(model=ch_model_probs, sess=sess)
            #x_adv_test_madry = madry_obj.generate(x=x, eps=fgsm_eps, eps_iter=fgsm_eps/10, nb_iter=10, clip_min=-1.0, clip_max=1.0, ord=2)
            x_adv_test_madry = madry_obj.generate(x=x,
                                                  eps=fgsm_eps,
                                                  eps_iter=fgsm_eps / 3,
                                                  nb_iter=3,
                                                  clip_min=-1.0,
                                                  clip_max=1.0)
            attack_tensor_dict['madry'] = x_adv_test_madry
        #====================== attack =========================

        correct_prediction = tf.equal(tf.argmax(y_conv, 1), tf.argmax(y_, 1))
        accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

        # Create a saver.
        saver = tf.train.Saver(tf.all_variables())

        # Privacy accountant
        priv_accountant = accountant.GaussianMomentsAccountant(D)
        privacy_accum_op = priv_accountant.accumulate_privacy_spending(
            [None, None], sigma, batch_size)

        # Build the summary operation based on the TF collection of Summaries.
        #summary_op = tf.summary.merge_all()

        # Build an initialization operation to run below.
        init = tf.initialize_all_variables()

        # Start running operations on the Graph.
        sess.run(init)

        # Start the queue runners.
        tf.train.start_queue_runners(sess=sess)

        summary_writer = tf.summary.FileWriter(os.getcwd() + path, sess.graph)

        # load the most recent models
        _global_step = 0
        ckpt = tf.train.get_checkpoint_state(FLAGS.checkpoint_dir)
        if ckpt and ckpt.model_checkpoint_path:
            print(ckpt.model_checkpoint_path)
            saver.restore(sess, ckpt.model_checkpoint_path)
            _global_step = int(
                ckpt.model_checkpoint_path.split('/')[-1].split('-')[-1])
        else:
            print('No checkpoint file found')

        T = int(int(math.ceil(D / batch_size)) * epochs + 1)  # number of steps
        step_for_epoch = int(math.ceil(D / batch_size))
        #number of steps for one epoch

        s = math.log(sqrt(2.0 / math.pi) * 1e+5)
        sigmaEGM = sqrt(2.0) * 1.0 * (sqrt(s) + sqrt(s + dp_epsilon)) / (
            2.0 * dp_epsilon)
        #print(sigmaEGM)
        __noiseE = np.random.normal(0.0, sigmaEGM,
                                    14 * 14 * 128).astype(np.float32)
        __noiseE = np.reshape(__noiseE, [-1, 14, 14, 128])
        print("Compute The Noise Redistribution Vector")
        for step in xrange(_global_step, 100 * step_for_epoch):
            batch = cifar10_data.train.next_batch(batch_size)
            #Get a random batch.
            _, loss_value = sess.run(
                [train_op, loss],
                feed_dict={
                    x: batch[0],
                    y_: batch[1],
                    noise: __noiseE * 0,
                    sigma: sigma_value * 0
                })
            if step % (5 * step_for_epoch) == 0:
                print(loss_value)
        batch = cifar10_data.train.next_batch(40 * batch_size)
        grad_redis = sess.run([normalized_grad_r],
                              feed_dict={
                                  x: batch[0],
                                  y_: batch[1],
                                  noise: __noiseE * 0
                              })
        _sensitivity_2 = sess.run([sensitivity_2],
                                  feed_dict={
                                      x: batch[0],
                                      y_: batch[1],
                                      noise: __noiseE * 0
                                  })
        #print(_sensitivity_2)

        _sensitivityW = sess.run(sensitivityW)
        #print(_sensitivityW)
        Delta_redis = _sensitivityW / sqrt(_sensitivity_2[0])
        #print(Delta_redis)
        sigmaHGM = sqrt(2.0) * Delta_redis * (
            sqrt(s) + sqrt(s + dp_epsilon)) / (2.0 * dp_epsilon)
        #print(sigmaHGM)
        __noiseH = np.random.normal(0.0, sigmaHGM,
                                    14 * 14 * 128).astype(np.float32)
        __noiseH = np.reshape(__noiseH, [-1, 14, 14, 128]) * grad_redis

        sess.run(init)
        print("Training")
        for step in xrange(_global_step, _global_step + T):
            start_time = time.time()
            batch = cifar10_data.train.next_batch(batch_size)
            #Get a random batch.
            #grad_redis = sess.run([normalized_grad_r], feed_dict = {x: batch[0], y_: batch[1], noise: (__noise + grad_redis)/2})
            _, loss_value = sess.run(
                [train_op, loss],
                feed_dict={
                    x: batch[0],
                    y_: batch[1],
                    noise: (__noiseE + __noiseH) / 2,
                    sigma: sigma_value
                })
            duration = time.time() - start_time

            assert not np.isnan(loss_value), 'Model diverged with loss = NaN'

            sess.run([privacy_accum_op])
            spent_eps_deltas = priv_accountant.get_privacy_spent(
                sess, target_eps=target_eps)
            if step % (5 * step_for_epoch) == 0:
                print(loss_value)
                print(spent_eps_deltas)
            _break = False
            for _eps, _delta in spent_eps_deltas:
                if _delta >= delta:
                    _break = True
                    break
            if _break == True:
                break

        ## Robustness
        print("Testing")
        adv_acc_dict = {}
        robust_adv_acc_dict = {}
        robust_adv_utility_dict = {}
        test_bach_size = 5000
        for atk in attack_switch.keys():
            if atk not in adv_acc_dict:
                adv_acc_dict[atk] = -1
                robust_adv_acc_dict[atk] = -1
                robust_adv_utility_dict[atk] = -1
            if attack_switch[atk]:
                test_bach = cifar10_data.test.next_batch(test_bach_size)
                adv_images_dict = sess.run(attack_tensor_dict[atk],
                                           feed_dict={x: test_bach[0]})
                ### PixelDP Robustness ###
                predictions_form_argmax = np.zeros([test_bach_size, 10])
                softmax_predictions = sess.run(softmax_y_conv,
                                               feed_dict={
                                                   x: adv_images_dict,
                                                   noise:
                                                   (__noiseE + __noiseH) / 2
                                               })
                argmax_predictions = np.argmax(softmax_predictions, axis=1)
                for n_draws in range(0, 1000):
                    _noiseE = np.random.normal(0.0, sigmaEGM, 14 * 14 *
                                               128).astype(np.float32)
                    _noiseE = np.reshape(_noiseE, [-1, 14, 14, 128])
                    _noise = np.random.normal(0.0, sigmaHGM,
                                              14 * 14 * 128).astype(np.float32)
                    _noise = np.reshape(_noise, [-1, 14, 14, 128]) * grad_redis
                    for j in range(test_bach_size):
                        pred = argmax_predictions[j]
                        predictions_form_argmax[j, pred] += 1
                    softmax_predictions = sess.run(
                        softmax_y_conv,
                        feed_dict={
                            x:
                            adv_images_dict,
                            noise:
                            (__noiseE + __noiseH) / 2 + (_noiseE + _noise) / 4
                        })
                    argmax_predictions = np.argmax(softmax_predictions, axis=1)
                final_predictions = predictions_form_argmax
                is_correct = []
                is_robust = []
                for j in range(test_bach_size):
                    is_correct.append(
                        np.argmax(test_bach[1][j]) == np.argmax(
                            final_predictions[j]))
                    robustness_from_argmax = robustnessGGaussian.robustness_size_argmax(
                        counts=predictions_form_argmax[j],
                        eta=0.05,
                        dp_attack_size=fgsm_eps,
                        dp_epsilon=dp_epsilon,
                        dp_delta=0.05,
                        dp_mechanism='gaussian') / dp_mult
                    is_robust.append(robustness_from_argmax >= fgsm_eps)
                adv_acc_dict[atk] = np.sum(is_correct) * 1.0 / test_bach_size
                robust_adv_acc_dict[atk] = np.sum([
                    a and b for a, b in zip(is_robust, is_correct)
                ]) * 1.0 / np.sum(is_robust)
                robust_adv_utility_dict[atk] = np.sum(
                    is_robust) * 1.0 / test_bach_size
                ##############################
        log_str = ""
        for atk in attack_switch.keys():
            if attack_switch[atk]:
                # added robust prediction
                log_str += " {}: {:.4f} {:.4f} {:.4f} {:.4f}".format(
                    atk, adv_acc_dict[atk], robust_adv_acc_dict[atk],
                    robust_adv_utility_dict[atk],
                    robust_adv_acc_dict[atk] * robust_adv_utility_dict[atk])
        print(log_str)
        logfile.write(log_str + '\n')
def Train(mnist_train_file,
          mnist_test_file,
          network_parameters,
          num_steps,
          save_path,
          eval_steps=0):
    """Train MNIST for a number of steps.

    Args:
      mnist_train_file: path of MNIST train data file.
      mnist_test_file: path of MNIST test data file.
      network_parameters: parameters for defining and training the network.
      num_steps: number of steps to run. Here steps = lots
      save_path: path where to save trained parameters.
      eval_steps: evaluate the model every eval_steps.

    Returns:
      the result after the final training step.

    Raises:
      ValueError: if the accountant_type is not supported.
    """
    batch_size = FLAGS.batch_size

    params = {
        "accountant_type": FLAGS.accountant_type,
        "task_id": 0,
        "batch_size": FLAGS.batch_size,
        "projection_dimensions": FLAGS.projection_dimensions,
        "default_gradient_l2norm_bound":
        network_parameters.default_gradient_l2norm_bound,
        "num_hidden_layers": FLAGS.num_hidden_layers,
        "hidden_layer_num_units": FLAGS.hidden_layer_num_units,
        "num_examples": NUM_TRAINING_IMAGES,
        "learning_rate": FLAGS.lr,
        "end_learning_rate": FLAGS.end_lr,
        "learning_rate_saturate_epochs": FLAGS.lr_saturate_epochs
    }
    # Log different privacy parameters dependent on the accountant type.
    if FLAGS.accountant_type == "Amortized":
        params.update({
            "flag_eps": FLAGS.eps,
            "flag_delta": FLAGS.delta,
            "flag_pca_eps": FLAGS.pca_eps,
            "flag_pca_delta": FLAGS.pca_delta,
        })
    elif FLAGS.accountant_type == "Moments":
        params.update({
            "sigma": FLAGS.sigma,
            "pca_sigma": FLAGS.pca_sigma,
        })

    with tf.Graph().as_default(), tf.Session() as sess, tf.device('/cpu:0'):
        # Create the basic Mnist model.
        images, labels = BRATSInput(is_train=True)

        logits, projection, training_params = utils.BuildNetwork(
            images, network_parameters)

        cost = tf.nn.softmax_cross_entropy_with_logits(logits=logits,
                                                       labels=tf.one_hot(
                                                           labels, 2))

        # The actual cost is the average across the examples.
        cost = tf.reduce_sum(cost, [0]) / batch_size

        if FLAGS.accountant_type == "Amortized":
            priv_accountant = accountant.AmortizedAccountant(
                NUM_TRAINING_IMAGES)
            sigma = None
            pca_sigma = None
            with_privacy = FLAGS.eps > 0
        elif FLAGS.accountant_type == "Moments":
            priv_accountant = accountant.GaussianMomentsAccountant(
                NUM_TRAINING_IMAGES)
            sigma = FLAGS.sigma
            pca_sigma = FLAGS.pca_sigma
            with_privacy = FLAGS.sigma > 0
        else:
            raise ValueError("Undefined accountant type, needs to be "
                             "Amortized or Moments, but got %s" %
                             FLAGS.accountant)
        # Note: Here and below, we scale down the l2norm_bound by
        # batch_size. This is because per_example_gradients computes the
        # gradient of the minibatch loss with respect to each individual
        # example, and the minibatch loss (for our model) is the *average*
        # loss over examples in the minibatch. Hence, the scale of the
        # per-example gradients goes like 1 / batch_size.
        gaussian_sanitizer = sanitizer.AmortizedGaussianSanitizer(
            priv_accountant, [
                network_parameters.default_gradient_l2norm_bound / batch_size,
                True
            ])

        for var in training_params:
            if "gradient_l2norm_bound" in training_params[var]:
                l2bound = training_params[var][
                    "gradient_l2norm_bound"] / batch_size
                gaussian_sanitizer.set_option(
                    var, sanitizer.ClipOption(l2bound, True))
        lr = tf.placeholder(tf.float32)
        eps = tf.placeholder(tf.float32)
        delta = tf.placeholder(tf.float32)

        init_ops = []
        if network_parameters.projection_type == "PCA":
            with tf.variable_scope("pca"):
                # Compute differentially private PCA.
                all_data, _ = BRATSInput(is_train=False)
                pca_projection = dp_pca.ComputeDPPrincipalProjection(
                    all_data, network_parameters.projection_dimensions,
                    gaussian_sanitizer, [FLAGS.pca_eps, FLAGS.pca_delta],
                    pca_sigma)
                assign_pca_proj = tf.assign(projection, pca_projection)
                init_ops.append(assign_pca_proj)

        # Add global_step
        global_step = tf.Variable(0,
                                  dtype=tf.int32,
                                  trainable=False,
                                  name="global_step")

        if with_privacy:
            gd_op = dp_optimizer.DPGradientDescentOptimizer(
                lr, [eps, delta],
                gaussian_sanitizer,
                sigma=sigma,
                batches_per_lot=FLAGS.batches_per_lot).minimize(
                    cost, global_step=global_step)
        else:
            gd_op = tf.train.GradientDescentOptimizer(lr).minimize(cost)

        saver = tf.train.Saver()
        coord = tf.train.Coordinator()
        _ = tf.train.start_queue_runners(sess=sess, coord=coord)

        # We need to maintain the intialization sequence.
        for v in tf.trainable_variables():
            sess.run(tf.variables_initializer([v]))
        sess.run(tf.global_variables_initializer())
        sess.run(init_ops)

        results = []
        start_time = time.time()
        prev_time = start_time
        filename = "results-0.json"
        log_path = os.path.join(save_path, filename)

        target_eps = [float(s) for s in FLAGS.target_eps.split(",")]
        if FLAGS.accountant_type == "Amortized":
            # Only matters if --terminate_based_on_privacy is true.
            target_eps = [max(target_eps)]
        max_target_eps = max(target_eps)

        lot_size = FLAGS.batches_per_lot * FLAGS.batch_size
        lots_per_epoch = NUM_TRAINING_IMAGES / lot_size
        for step in range(num_steps):
            epoch = step / lots_per_epoch
            curr_lr = utils.VaryRate(FLAGS.lr, FLAGS.end_lr,
                                     FLAGS.lr_saturate_epochs, epoch)
            curr_eps = utils.VaryRate(FLAGS.eps, FLAGS.end_eps,
                                      FLAGS.eps_saturate_epochs, epoch)
            for _ in range(FLAGS.batches_per_lot):
                _ = sess.run([gd_op],
                             feed_dict={
                                 lr: curr_lr,
                                 eps: curr_eps,
                                 delta: FLAGS.delta
                             })
            sys.stderr.write("step: %d\n" % step)

            # See if we should stop training due to exceeded privacy budget:
            should_terminate = False
            terminate_spent_eps_delta = None
            if with_privacy and FLAGS.terminate_based_on_privacy:
                terminate_spent_eps_delta = priv_accountant.get_privacy_spent(
                    sess, target_eps=[max_target_eps])[0]
                # For the Moments accountant, we should always have
                # spent_eps == max_target_eps.
                if (terminate_spent_eps_delta.spent_delta > FLAGS.target_delta
                        or
                        terminate_spent_eps_delta.spent_eps > max_target_eps):
                    should_terminate = True

            if (eval_steps > 0 and
                (step + 1) % eval_steps == 0) or should_terminate:
                if with_privacy:
                    spent_eps_deltas = priv_accountant.get_privacy_spent(
                        sess, target_eps=target_eps)
                else:
                    spent_eps_deltas = [accountant.EpsDelta(0, 0)]
                for spent_eps, spent_delta in spent_eps_deltas:
                    sys.stderr.write("spent privacy: eps %.4f delta %.5g\n" %
                                     (spent_eps, spent_delta))

                saver.save(sess, save_path=save_path + "/ckpt")
                train_accuracy, _ = Eval(mnist_train_file,
                                         network_parameters,
                                         num_testing_images=NUM_TESTING_IMAGES,
                                         randomize=True,
                                         load_path=save_path)
                sys.stderr.write("train_accuracy: %.2f\n" % train_accuracy)
                test_accuracy, mistakes = Eval(
                    mnist_test_file,
                    network_parameters,
                    num_testing_images=NUM_TESTING_IMAGES,
                    randomize=False,
                    load_path=save_path,
                    save_mistakes=FLAGS.save_mistakes)
                sys.stderr.write("eval_accuracy: %.2f\n" % test_accuracy)

                curr_time = time.time()
                elapsed_time = curr_time - prev_time
                prev_time = curr_time

                results.append({
                    "step": step + 1,  # Number of lots trained so far.
                    "elapsed_secs": elapsed_time,
                    "spent_eps_deltas": spent_eps_deltas,
                    "train_accuracy": train_accuracy,
                    "test_accuracy": test_accuracy,
                    "mistakes": mistakes
                })
                loginfo = {
                    "elapsed_secs": curr_time - start_time,
                    "spent_eps_deltas": spent_eps_deltas,
                    "train_accuracy": train_accuracy,
                    "test_accuracy": test_accuracy,
                    "num_training_steps": step + 1,  # Steps so far.
                    "mistakes": mistakes,
                    "result_series": results
                }
                loginfo.update(params)
                if log_path:
                    with tf.gfile.Open(log_path, "w") as f:
                        json.dump(loginfo, f, indent=2)
                        f.write("\n")
                        f.close()

            if should_terminate:
                break
Exemple #6
0
def main(_):
    clip_bound = 0.01  # 'the clip bound of the gradients'
    clip_bound_2 = 1 / 1.5  #'the clip bound for r_kM'

    small_num = 1e-5  # 'a small number'
    large_num = 1e5  # a large number'
    num_images = 60000  # 'number of images N'

    batch_size = 600  # 'batch_size L'
    sample_rate = 600 / 60000  # 'sample rate q = L / N'
    num_steps = 160000  # 'number of steps T = E * N / L = E / q'
    num_epoch = 24  # 'number of epoches E'

    sigma = 5  # 'sigma'
    delta = 1e-5  # 'delta'

    lambd = 1e3  # 'exponential distribution parameter'

    iterative_clip_step = 2  # 'iterative_clip_step'

    clip = 1  # 'whether to clip the gradient'
    noise = 0  # 'whether to add noise'
    redistribute = 0  # 'whether to redistribute the noise'

    D = 60000
    '''from tensorflow.examples.tutorials.mnist import input_data;
  mnist = input_data.read_data_sets(FLAGS.data_dir, one_hot=True);'''

    sess = tf.InteractiveSession()

    # Create the model
    x = tf.placeholder(tf.float32, [None, 784])
    x_image = tf.reshape(x, [-1, 28, 28, 1])
    W_conv1 = weight_variable([5, 5, 1, 32])
    b_conv1 = bias_variable([32])
    h_conv1 = tf.nn.relu(conv2d(x_image, W_conv1) + b_conv1)
    h_pool1 = max_pool_2x2(h_conv1)

    W_conv2 = weight_variable([5, 5, 32, 64])
    b_conv2 = bias_variable([64])
    h_conv2 = tf.nn.relu(conv2d(h_pool1, W_conv2) + b_conv2)
    h_pool2 = max_pool_2x2(h_conv2)

    W_fc1 = weight_variable([7 * 7 * 64, 25])
    b_fc1 = bias_variable([25])
    h_pool2_flat = tf.reshape(h_pool2, [-1, 7 * 7 * 64])
    h_fc1 = tf.nn.relu(tf.matmul(h_pool2_flat, W_fc1) + b_fc1)

    keep_prob = tf.placeholder(tf.float32)
    h_fc1_drop = tf.nn.dropout(h_fc1, keep_prob)

    W_fc2 = weight_variable([25, 10])
    b_fc2 = bias_variable([10])
    y_conv = tf.matmul(h_fc1_drop, W_fc2) + b_fc2

    # Define loss and optimizer
    y_ = tf.placeholder(tf.float32, [None, 10])

    d = 25 * 10 + 25 * 7 * 7 * 64 + 5 * 5 * 32 * 64 + 5 * 5 * 32
    # number of parameters
    M = d

    priv_accountant = accountant.GaussianMomentsAccountant(D)
    privacy_accum_op = priv_accountant.accumulate_privacy_spending(
        [None, None], sigma, batch_size)

    #sess.run(tf.initialize_all_variables())
    sess.run(tf.global_variables_initializer())

    cross_entropy = tf.reduce_mean(
        tf.nn.softmax_cross_entropy_with_logits(labels=y_, logits=y_conv))
    #train_step = tf.train.AdamOptimizer(1e-5).minimize(cross_entropy);
    #train_step = tf.train.AdamOptimizer(1e-5).minimize(cross_entropy)

    opt = GradientDescentOptimizer(learning_rate=1e-2)

    #compute gradient
    gw_W1 = tf.gradients(cross_entropy, W_conv1)[0]  # gradient of W1
    gb1 = tf.gradients(cross_entropy, b_conv1)[0]  # gradient of b1

    gw_W2 = tf.gradients(cross_entropy, W_conv2)[0]  # gradient of W2
    gb2 = tf.gradients(cross_entropy, b_conv2)[0]  # gradient of b2

    gw_Wf1 = tf.gradients(cross_entropy, W_fc1)[0]  # gradient of W_fc1
    gbf1 = tf.gradients(cross_entropy, b_fc1)[0]  # gradient of b_fc1

    gw_Wf2 = tf.gradients(cross_entropy, W_fc2)[0]  # gradient of W_fc2
    gbf2 = tf.gradients(cross_entropy, b_fc2)[0]  # gradient of b_fc2

    #clip gradient
    gw_W1 = tf.clip_by_norm(gw_W1, clip_bound)
    gw_W2 = tf.clip_by_norm(gw_W2, clip_bound)
    gw_Wf1 = tf.clip_by_norm(gw_Wf1, clip_bound)
    gw_Wf2 = tf.clip_by_norm(gw_Wf2, clip_bound)

    #sigma = FLAGS.sigma # when comp_eps(lmbda,q,sigma,T,delta)==epsilon

    #sensitivity = 2 * FLAGS.clip_bound #adjacency matrix with one tuple different
    sensitivity = clip_bound  #adjacency matrix with one more tuple

    gw_W1 += tf.random_normal(shape=tf.shape(gw_W1),
                              mean=0.0,
                              stddev=(sigma * sensitivity)**2,
                              dtype=tf.float32)
    gb1 += tf.random_normal(shape=tf.shape(gb1),
                            mean=0.0,
                            stddev=(sigma * sensitivity)**2,
                            dtype=tf.float32)
    gw_W2 += tf.random_normal(shape=tf.shape(gw_W2),
                              mean=0.0,
                              stddev=(sigma * sensitivity)**2,
                              dtype=tf.float32)
    gb2 += tf.random_normal(shape=tf.shape(gb2),
                            mean=0.0,
                            stddev=(sigma * sensitivity)**2,
                            dtype=tf.float32)
    gw_Wf1 += tf.random_normal(shape=tf.shape(gw_Wf1),
                               mean=0.0,
                               stddev=(sigma * sensitivity)**2,
                               dtype=tf.float32)
    gbf1 += tf.random_normal(shape=tf.shape(gbf1),
                             mean=0.0,
                             stddev=(sigma * sensitivity)**2,
                             dtype=tf.float32)
    gw_Wf2 += tf.random_normal(shape=tf.shape(gw_Wf2),
                               mean=0.0,
                               stddev=(sigma * sensitivity)**2,
                               dtype=tf.float32)
    gbf2 += tf.random_normal(shape=tf.shape(gbf2),
                             mean=0.0,
                             stddev=(sigma * sensitivity)**2,
                             dtype=tf.float32)

    train_step = opt.apply_gradients([(gw_W1, W_conv1), (gb1, b_conv1),
                                      (gw_W2, W_conv2), (gb2, b_conv2),
                                      (gw_Wf1, W_fc1), (gbf1, b_fc1),
                                      (gw_Wf2, W_fc2), (gbf2, b_fc2)])

    correct_prediction = tf.equal(tf.argmax(y_conv, 1), tf.argmax(y_, 1))
    accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

    start_time = time.time()
    for i in range(num_steps):
        batch = mnist.train.next_batch(batch_size)
        train_step.run(feed_dict={
            x: batch[0],
            y_: batch[1],
            keep_prob: 0.5
        })

        if i % 100 == 0:
            #train_accuracy = accuracy.eval(feed_dict={x:batch[0], y_: batch[1], keep_prob: 1.0});
            #print("step \t %d \t training accuracy \t %g"%(i, train_accuracy));
            print("step \t %d \t test accuracy \t %g" %
                  (i,
                   accuracy.eval(feed_dict={
                       x: mnist.test.images,
                       y_: mnist.test.labels,
                       keep_prob: 1.0
                   })))
            #epsilon = comp_eps(32, sample_rate, sigma, i, delta)
            #print("epsilon: {}".format(epsilon))
        sess.run([privacy_accum_op])
        spent_eps_deltas = priv_accountant.get_privacy_spent(
            sess, target_eps=target_eps)
        #print(i, spent_eps_deltas)
        _break = False
        for _eps, _delta in spent_eps_deltas:
            if _delta >= delta:
                _break = True
                break
        if _break == True:
            break
    duration = time.time() - start_time
    print("test accuracy %g" % accuracy.eval(feed_dict={
        x: mnist.test.images,
        y_: mnist.test.labels,
        keep_prob: 1.0
    }))
    print(float(duration))
Exemple #7
0
def PDP_SSGD_resnet_with_pretrain(TIN_data, resnet_params, train_params,
                                  params_to_save):
    # dict for encoding layer variables and output layer variables
    pre_define_vars = {}

    # list of variables to train
    train_vars = []

    with tf.Graph().as_default(), tf.device('/cpu:0'):
        global_step = tf.Variable(0, trainable=False)

        # Parameters Declarification
        ######################################

        # encoding (pretrain) layer variables
        with tf.variable_scope('enc_layer', reuse=tf.AUTO_REUSE) as scope:
            kernel1 = tf.get_variable(
                'kernel1',
                shape=[
                    train_params.enc_kernel_size, train_params.enc_kernel_size,
                    3, train_params.enc_filters
                ],
                dtype=tf.float32,
                initializer=tf.contrib.layers.xavier_initializer_conv2d())
            biases1 = tf.get_variable('biases1',
                                      shape=[train_params.enc_filters],
                                      dtype=tf.float32,
                                      initializer=tf.constant_initializer(0.0))
        pre_define_vars['kernel1'] = kernel1
        pre_define_vars['biases1'] = biases1
        train_vars.append(kernel1)
        train_vars.append(biases1)

        shape = kernel1.get_shape().as_list()
        w_t = tf.reshape(kernel1, [-1, shape[-1]])
        w = tf.transpose(w_t)
        sing_vals = tf.svd(w, compute_uv=False)
        sensitivityW = tf.reduce_max(sing_vals)
        dp_mult = train_params.attack_norm_bound * math.sqrt(2 * math.log(
            1.25 / train_params.dp_delta)) / train_params.dp_epsilon
        params_to_save['dp_mult'] = dp_mult

        # output layer variables
        with tf.variable_scope('fc2', reuse=tf.AUTO_REUSE) as scope:
            stdv = 1.0 / math.sqrt(train_params.hk)
            final_w = tf.get_variable(
                'kernel',
                shape=[train_params.hk, train_params.num_classes],
                dtype=tf.float32,
                initializer=tf.random_uniform_initializer(-stdv, stdv))
            final_b = tf.get_variable('bias',
                                      shape=[train_params.num_classes],
                                      dtype=tf.float32,
                                      initializer=tf.constant_initializer(0.0))
        pre_define_vars['final_w'] = final_w
        pre_define_vars['final_b'] = final_b
        train_vars.append(final_w)
        train_vars.append(final_b)
        ######################################

        # Build a Graph that computes the logits predictions from the inputs
        ######################################
        # input placeholders
        x_sb = tf.placeholder(
            tf.float32,
            [None, train_params.image_size, train_params.image_size, 3],
            name='x_sb')  # input is the bunch of n_batchs
        x_test = tf.placeholder(
            tf.float32,
            [None, train_params.image_size, train_params.image_size, 3],
            name='x_test')

        y_sb = tf.placeholder(
            tf.float32, [None, train_params.num_classes],
            name='y_sb')  # input is the bunch of n_batchs (super batch)
        y_test = tf.placeholder(tf.float32, [None, train_params.num_classes],
                                name='y_test')

        noise = tf.placeholder(tf.float32, [
            None, train_params.enc_h_size, train_params.enc_h_size,
            train_params.enc_filters
        ],
                               name='noise')  # one time

        learning_rate = tf.placeholder(tf.float32,
                                       shape=(),
                                       name='learning_rate')
        keep_prob = tf.placeholder(tf.float32, shape=(), name='keep_prob')

        # list of grads for each GPU
        tower_pretrain_grads = []
        tower_train_grads = []
        all_train_loss = []

        # optimizers
        train_opt = tf.train.GradientDescentOptimizer(learning_rate)

        with tf.device('/gpu:0'):
            # the model
            y_logits, h_conv1 = inference(
                x_sb, train_params.attack_norm_bound * noise, keep_prob,
                pre_define_vars, resnet_params, train_params)
            y_softmax = tf.nn.softmax(y_logits)

            # loss
            with tf.device('/cpu:0'):
                loss = lossDPSGD(y_logits, y_sb)
            # get total loss tensor for train ops
            total_loss = tf.reduce_sum(loss)

            # noise redistribution parameters
            grad, = tf.gradients(loss, h_conv1)
            print(loss)
            print(h_conv1)
            print(grad)
            normalized_grad = tf.sign(grad)
            normalized_grad = tf.stop_gradient(normalized_grad)
            normalized_grad_r = tf.abs(
                tf.reduce_mean(normalized_grad, axis=(0)))**2
            sum_r = tf.reduce_sum(normalized_grad_r,
                                  axis=(0, 1, 2),
                                  keepdims=False)
            normalized_grad_r = train_params.enc_h_size * train_params.enc_h_size * train_params.enc_filters * normalized_grad_r / sum_r
            shape_grad = normalized_grad_r.get_shape().as_list()
            grad_t = tf.reshape(normalized_grad_r, [-1, shape_grad[-1]])
            g = tf.transpose(grad_t)
            sing_g_vals = tf.svd(g, compute_uv=False)
            sensitivity_2 = tf.reduce_max(sing_g_vals)

            y_logits_test, _ = test_inference(
                x_sb, train_params.attack_norm_bound * noise, keep_prob,
                pre_define_vars, resnet_params, train_params)
            y_softmax_test = tf.nn.softmax(y_logits_test)
        correct_prediction = tf.equal(tf.argmax(y_logits_test, 1),
                                      tf.argmax(y_sb, 1))
        accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

        priv_accountant = accountant.GaussianMomentsAccountant(
            train_params.train_size)
        privacy_accum_op = priv_accountant.accumulate_privacy_spending(
            [None, None], train_params.sigma, train_params.batch_size)

        # print all variables
        print('$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$')
        all_vars = tf.global_variables()
        print_var_list('all vars', all_vars)
        print('$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$')

        # add selected vars into list
        # ('res4' in var.name and ('gamma' in var.name or 'beta' in var.name)) or
        for var in tf.global_variables():
            if 'resnet_model' in var.name and \
              ('conv0' in var.name or
              'fc' in var.name or
              'res3' in var.name or
              'res4' in var.name or
              'res1' in var.name or
              'res2' in var.name) and \
                ('gamma' in var.name or
                  'beta' in var.name or
                  'kernel' in var.name or
                  'bias' in var.name):
                if var not in train_vars:
                    train_vars.append(var)
            elif 'enc_layer' in var.name and \
              ('kernel' in var.name or
                'bias' in var.name or
                'gamma' in var.name or
                'beta' in var.name):
                if var not in train_vars:
                    train_vars.append(var)

        print_var_list('train_vars', train_vars)
        print('$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$')

        # op for compute grads
        with tf.device('/gpu:0'):
            # get all update_ops (updates of moving averageand std) for batch normalizations
            update_ops = tf.get_collection(tf.GraphKeys.UPDATE_OPS)
            print_op_list('update ops', update_ops)

            # compute each gradient and apply clip and noise
            train_grads = []
            for var in train_vars:
                g = tf.clip_by_norm(
                    tf.gradients(loss, var)[0], train_params.clip_bound)
                g = g + tf.random_normal(shape=tf.shape(g),
                                         mean=0.0,
                                         stddev=train_params.sigma *
                                         (train_params.sensitivity**2),
                                         dtype=tf.float32)
                train_grads.append((g, var))

        # now the train and pretrain ops do not come with update_ops
        with tf.control_dependencies(update_ops):
            train_op = train_opt.apply_gradients(train_grads,
                                                 global_step=global_step)

        ######################################

        # Create a saver.
        saver = tf.train.Saver(var_list=tf.all_variables(), max_to_keep=1000)

        # start a session with memory growth
        config = tf.ConfigProto(log_device_placement=False)
        config.gpu_options.allow_growth = True
        sess = tf.Session(config=config)
        print("session created")

        # init op
        print('initialize_all_variables')
        init = tf.initialize_all_variables()
        sess.run(init)

        if train_params.load_weights:
            # load pretrained variables
            # load variable convert table
            tgt_var_name_dict = {}
            with open(train_params.weight_table_path, 'r',
                      encoding='utf-8') as inf:
                lines = inf.readlines()
                for line in lines:
                    var_names = line.strip().split(' ')
                    if var_names[1] == 'NONE':
                        continue
                    else:
                        tgt_var_name_dict[var_names[0]] = var_names[1]

            # load variables
            pretrained_var_dict = load_pretrained_vars()

            # load pre-trained vars
            for var in tf.global_variables():
                if var.name in tgt_var_name_dict:
                    # print('var \"{}\" found'.format(var.name))
                    try:
                        var.load(
                            pretrained_var_dict[tgt_var_name_dict[var.name]],
                            session=sess)
                        print('{} loaded'.format(var.name))
                    except:
                        print('var {} not loaded since shape changed'.format(
                            var.name))
                else:
                    if 'Adam' not in var.name:
                        print('var \"{}\" NOT FOUND'.format(var.name))
        else:
            print('Training model from scratch')

        #####################################
        # init noise

        s = math.log(sqrt(2.0 / math.pi) * 1e+5)
        sigmaEGM = sqrt(2.0) * 1.0 * (sqrt(s) +
                                      sqrt(s + train_params.dp_epsilon)) / (
                                          2.0 * train_params.dp_epsilon)
        params_to_save['sigmaEGM'] = sigmaEGM

        __noiseE = np.random.normal(
            0.0, sigmaEGM**2,
            train_params.enc_h_size * train_params.enc_h_size *
            train_params.enc_filters).astype(np.float32)
        __noiseE = np.reshape(__noiseE, [
            -1, train_params.enc_h_size, train_params.enc_h_size,
            train_params.enc_filters
        ])
        params_to_save['__noiseE'] = __noiseE

        _batch = TIN_data.train.next_super_batch(5,
                                                 ensemble=False,
                                                 random=True)
        grad_redis = sess.run([normalized_grad_r],
                              feed_dict={
                                  x_sb: _batch[0],
                                  y_sb: _batch[1],
                                  noise: __noiseE * 0,
                                  keep_prob: 1.0
                              })
        params_to_save['grad_redis'] = grad_redis

        _sensitivity_2 = sess.run([sensitivity_2],
                                  feed_dict={
                                      x_sb: _batch[0],
                                      y_sb: _batch[1],
                                      noise: __noiseE * 0,
                                      keep_prob: 1.0
                                  })
        params_to_save['_sensitivity_2'] = _sensitivity_2

        _sensitivityW = sess.run(sensitivityW)
        params_to_save['_sensitivityW'] = _sensitivityW

        Delta_redis = _sensitivityW / sqrt(_sensitivity_2[0])
        params_to_save['Delta_redis'] = Delta_redis

        sigmaHGM = sqrt(2.0) * Delta_redis * (
            sqrt(s) + sqrt(s + train_params.dp_epsilon)) / (
                2.0 * train_params.dp_epsilon)
        params_to_save['sigmaHGM'] = sigmaHGM

        __noiseH = np.random.normal(
            0.0, sigmaHGM**2,
            train_params.enc_h_size * train_params.enc_h_size *
            train_params.enc_filters).astype(np.float32)
        __noiseH = np.reshape(__noiseH, [
            -1, train_params.enc_h_size, train_params.enc_h_size,
            train_params.enc_filters
        ]) * grad_redis
        params_to_save['__noiseH'] = __noiseH

        __noise_zero = np.random.normal(
            0.0, 0, train_params.enc_h_size * train_params.enc_h_size *
            train_params.enc_filters).astype(np.float32)
        __noise_zero = np.reshape(__noise_zero, [
            -1, train_params.enc_h_size, train_params.enc_h_size,
            train_params.enc_filters
        ])
        params_to_save['__noise_zero'] = __noise_zero

        # save params
        with open(os.getcwd() + train_params.params_save_path, 'wb') as outf:
            pickle.dump(params_to_save, outf)
            print('params saved')

        ####################################

        ####################################
        print('start train')
        start_time = time.time()
        lr_schedule_list = sorted(train_params.lr_schedule.keys())
        # train whole model
        step = 0
        while True:
            # if enough steps, break
            if step > train_params.train_steps:
                break
            # add steps here so not forgot
            else:
                step += 1

            # manual schedule learning rate
            current_epoch = step // (train_params.epoch_steps)
            current_lr = train_params.lr_schedule[get_lr(
                current_epoch, lr_schedule_list)]

            # benign and adv batch
            super_batch = TIN_data.train.next_super_batch(1,
                                                          ensemble=False,
                                                          random=True)

            _, loss_value = sess.run(
                [train_op, loss],
                feed_dict={
                    x_sb: super_batch[0],
                    y_sb: super_batch[1],
                    noise: (__noiseE + __noiseH) / 2,
                    keep_prob: train_params.keep_prob,
                    learning_rate: current_lr
                })

            # check with the privacy budget
            sess.run([privacy_accum_op])
            spent_eps_deltas = priv_accountant.get_privacy_spent(
                sess, target_eps=train_params.target_eps)
            if step % int(train_params.epoch_steps) == 0:
                print(spent_eps_deltas)
            _break = False
            for _eps, _delta in spent_eps_deltas:
                if _delta >= train_params.delta:
                    _break = True
                    break
            if _break == True:
                print('budget all spent, stop training')
                break

            # print status every epoch
            if step % int(train_params.epoch_steps) == 0:
                dt = time.time() - start_time
                avg_epoch_time = dt / (step / train_params.epoch_steps)
                print('epoch: {:.4f}, avg epoch time: {:.4f}s, current_lr: {}'.
                      format(step / train_params.epoch_steps, avg_epoch_time,
                             current_lr),
                      flush=True)
                print('train_loss: {:.6f}'.format(loss_value))

            # save model
            if step % int(train_params.epoch_steps) == 0 and int(
                    step /
                    train_params.epoch_steps) in train_params.epochs_to_save:
                print('saving model at epoch {}'.format(
                    step / train_params.epoch_steps))
                checkpoint_path = os.path.join(
                    os.getcwd() + train_params.check_point_dir, 'model.ckpt')
                saver.save(sess, checkpoint_path, global_step=step)

            # for testing, I use basic inference procedure and accuracy measure on only benign data
            # if step % int(train_params.epoch_steps) == 0 and int(step / train_params.epoch_steps) in train_params.epochs_to_test:
            if step % int(10 * train_params.epoch_steps) == 0 and step > 0:
                test_start = time.time()
                print('train test reported at step: {}, epoch: {}'.format(
                    step, step / train_params.epoch_steps))
                dt = time.time() - start_time
                avg_epoch_time = dt / (step / train_params.epoch_steps)
                print('epoch: {:.4f}, avg epoch time: {:.4f}s, current_lr: {}'.
                      format(step / train_params.epoch_steps, avg_epoch_time,
                             current_lr),
                      flush=True)
                print('train_loss: {:.6f}'.format(loss_value))
                # print('output layer: \n\t{}'.format(output_layer_value))

                #===================adv samples=====================
                adv_acc = 0.0
                robust_adv_acc = 0.0
                robust_adv_utility = 0.0
                log_str = ''
                # cover all test data
                for i in range(train_params.test_epochs):
                    # start testing
                    test_batch = TIN_data.test.next_batch(
                        train_params.test_batch_size)
                    ### PixelDP Robustness ###
                    predictions_form_argmax = np.zeros([
                        train_params.test_batch_size, train_params.num_classes
                    ])
                    softmax_predictions = sess.run(
                        y_softmax_test,
                        feed_dict={
                            x_sb: test_batch[0],
                            noise: (__noiseE + __noiseH) / 2,
                            keep_prob: 1.0
                        })
                    argmax_predictions = np.argmax(softmax_predictions, axis=1)
                    for n_draws in range(0, train_params.num_samples):
                        _noiseE = np.random.normal(
                            0.0, sigmaEGM**2,
                            train_params.enc_h_size * train_params.enc_h_size *
                            train_params.enc_filters).astype(np.float32)
                        _noiseE = np.reshape(_noiseE, [
                            -1, train_params.enc_h_size,
                            train_params.enc_h_size, train_params.enc_filters
                        ])
                        _noise = np.random.normal(
                            0.0, sigmaHGM**2,
                            train_params.enc_h_size * train_params.enc_h_size *
                            train_params.enc_filters).astype(np.float32)
                        _noise = np.reshape(_noise, [
                            -1, train_params.enc_h_size,
                            train_params.enc_h_size, train_params.enc_filters
                        ]) * grad_redis
                        for j in range(train_params.test_batch_size):
                            pred = argmax_predictions[j]
                            predictions_form_argmax[j, pred] += 1
                        softmax_predictions = sess.run(
                            y_softmax_test,
                            feed_dict={
                                x_sb:
                                test_batch[0],
                                noise: (__noiseE + __noiseH) / 2 +
                                (_noiseE + _noise) / 4,
                                keep_prob:
                                1.0
                            })
                        argmax_predictions = np.argmax(softmax_predictions,
                                                       axis=1)
                    final_predictions = predictions_form_argmax
                    is_correct = []
                    is_robust = []
                    for j in range(train_params.test_batch_size):
                        is_correct.append(
                            np.argmax(test_batch[1][j]) == np.argmax(
                                final_predictions[j]))
                        robustness_from_argmax = robustnessGGaussian.robustness_size_argmax(
                            counts=predictions_form_argmax[j],
                            eta=0.05,
                            dp_attack_size=train_params.fgsm_eps,
                            dp_epsilon=train_params.dp_epsilon,
                            dp_delta=0.05,
                            dp_mechanism='gaussian') / dp_mult
                        is_robust.append(
                            robustness_from_argmax >= train_params.fgsm_eps)
                    adv_acc += np.sum(
                        is_correct) * 1.0 / train_params.test_batch_size
                    robust_adv_acc += np.sum([
                        a and b for a, b in zip(is_robust, is_correct)
                    ]) * 1.0 / np.sum(is_robust)
                    robust_adv_utility += np.sum(
                        is_robust) * 1.0 / train_params.test_batch_size
                ##############################
                # average all acc for whole test data
                adv_acc = adv_acc / train_params.test_epochs
                robust_adv_acc = robust_adv_acc / train_params.test_epochs
                robust_adv_utility = robust_adv_utility / train_params.test_epochs
                log_str += " {}: {:.6f} {:.6f} {:.6f} {:.6f}\n".format(
                    'benign', adv_acc, robust_adv_acc, robust_adv_utility,
                    robust_adv_acc * robust_adv_utility)
                dt = time.time() - test_start
                print('testing time: {}'.format(dt))
                print(log_str, flush=True)
                print('*******************')
Exemple #8
0
def train(fgsm_eps, _dp_epsilon, _attack_norm_bound, log_filename, ratio):
    FLAGS = None

    #ratio = 16
    #target_eps = [0.125,0.25,0.5,1,2,4,8]
    #target_eps = [0.25 + 0.25*ratio]
    target_eps = [0.2 + 0.2 * ratio]
    #print(target_eps[0])
    #fgsm_eps = 0.1
    dp_epsilon = _dp_epsilon
    image_size = 28
    _log_filename = log_filename + str(target_eps[0]) + '_fgsm_' + str(
        fgsm_eps) + '_dpeps_' + str(dp_epsilon) + '_attack_norm_bound_' + str(
            _attack_norm_bound) + '.txt'

    clip_bound = 0.001  # 'the clip bound of the gradients'
    clip_bound_2 = 1 / 1.5  # 'the clip bound for r_kM'

    small_num = 1e-5  # 'a small number'
    large_num = 1e5  # a large number'
    num_images = 50000  # 'number of images N'

    batch_size = 125  # 'batch_size L'
    sample_rate = batch_size / 50000  # 'sample rate q = L / N'
    # 900 epochs
    num_steps = 1800000  # 'number of steps T = E * N / L = E / q'
    num_epoch = 24  # 'number of epoches E'

    sigma = 5  # 'sigma'
    delta = 1e-5  # 'delta'

    lambd = 1e3  # 'exponential distribution parameter'

    iterative_clip_step = 2  # 'iterative_clip_step'

    clip = 1  # 'whether to clip the gradient'
    noise = 0  # 'whether to add noise'
    redistribute = 0  # 'whether to redistribute the noise'

    D = 50000

    sess = tf.InteractiveSession()

    # Create the model
    x = tf.placeholder(tf.float32, [None, 784])
    y_ = tf.placeholder(tf.float32, [None, 10])
    keep_prob = tf.placeholder(tf.float32)

    W_conv1 = weight_variable([5, 5, 1, 32])
    b_conv1 = bias_variable([32])
    W_conv2 = weight_variable([5, 5, 32, 64])
    b_conv2 = bias_variable([64])
    W_fc1 = weight_variable([7 * 7 * 64, 25])
    b_fc1 = bias_variable([25])
    W_fc2 = weight_variable([25, 10])
    b_fc2 = bias_variable([10])

    def inference(x, dp_mult):
        x_image = tf.reshape(x, [-1, 28, 28, 1])
        h_conv1 = tf.nn.relu((conv2d(x_image, W_conv1) + b_conv1) + dp_mult)
        h_pool1 = max_pool_2x2(h_conv1)
        h_conv2 = tf.nn.relu(conv2d(h_pool1, W_conv2) + b_conv2)
        h_pool2 = max_pool_2x2(h_conv2)
        h_pool2_flat = tf.reshape(h_pool2, [-1, 7 * 7 * 64])
        h_fc1 = tf.nn.relu(tf.matmul(h_pool2_flat, W_fc1) + b_fc1)
        h_fc1_drop = tf.nn.dropout(h_fc1, keep_prob)

        y_conv = tf.matmul(h_fc1_drop, W_fc2) + b_fc2
        return y_conv, h_conv1

    def inference_prob(x):
        logits, _ = inference(x, 0)
        y_prob = tf.nn.softmax(logits)
        return y_prob

    shape = W_conv1.get_shape().as_list()
    w_t = tf.reshape(W_conv1, [-1, shape[-1]])
    w = tf.transpose(w_t)
    sing_vals = tf.svd(w, compute_uv=False)
    sensitivityW = tf.reduce_max(sing_vals)
    dp_delta = 0.05
    attack_norm_bound = _attack_norm_bound
    dp_mult = attack_norm_bound * math.sqrt(
        2 * math.log(1.25 / dp_delta)) / dp_epsilon
    noise = tf.placeholder(tf.float32, [None, 28, 28, 32])

    #y_conv, h_conv1 = inference(x, dp_mult * noise)
    y_conv, h_conv1 = inference(x, attack_norm_bound * noise)
    softmax_y = tf.nn.softmax(y_conv)
    # Define loss and optimizer

    priv_accountant = accountant.GaussianMomentsAccountant(D)
    privacy_accum_op = priv_accountant.accumulate_privacy_spending(
        [None, None], sigma, batch_size)

    # sess.run(tf.initialize_all_variables())
    sess.run(tf.global_variables_initializer())

    cross_entropy = tf.reduce_mean(
        tf.nn.softmax_cross_entropy_with_logits(labels=y_, logits=y_conv))
    #train_step = tf.train.AdamOptimizer(1e-5).minimize(cross_entropy);
    #train_step = tf.train.AdamOptimizer(1e-5).minimize(cross_entropy)

    # noise redistribution #
    grad, = tf.gradients(cross_entropy, h_conv1)
    normalized_grad = tf.sign(grad)
    normalized_grad = tf.stop_gradient(normalized_grad)
    normalized_grad_r = tf.abs(tf.reduce_mean(normalized_grad, axis=(0)))
    #print(normalized_grad_r)
    sum_r = tf.reduce_sum(normalized_grad_r, axis=(0, 1, 2), keepdims=False)
    #print(sum_r)
    normalized_grad_r = 256 * 32 * normalized_grad_r / sum_r
    print(normalized_grad_r)

    shape_grad = normalized_grad_r.get_shape().as_list()
    grad_t = tf.reshape(normalized_grad_r, [-1, shape_grad[-1]])
    g = tf.transpose(grad_t)
    sing_g_vals = tf.svd(g, compute_uv=False)
    sensitivity_2 = tf.reduce_max(sing_g_vals)
    ########################

    opt = GradientDescentOptimizer(learning_rate=1e-1)

    # compute gradient
    gw_W1 = tf.gradients(cross_entropy, W_conv1)[0]  # gradient of W1
    gb1 = tf.gradients(cross_entropy, b_conv1)[0]  # gradient of b1

    gw_W2 = tf.gradients(cross_entropy, W_conv2)[0]  # gradient of W2
    gb2 = tf.gradients(cross_entropy, b_conv2)[0]  # gradient of b2

    gw_Wf1 = tf.gradients(cross_entropy, W_fc1)[0]  # gradient of W_fc1
    gbf1 = tf.gradients(cross_entropy, b_fc1)[0]  # gradient of b_fc1

    gw_Wf2 = tf.gradients(cross_entropy, W_fc2)[0]  # gradient of W_fc2
    gbf2 = tf.gradients(cross_entropy, b_fc2)[0]  # gradient of b_fc2

    # clip gradient
    gw_W1 = tf.clip_by_norm(gw_W1, clip_bound)
    gw_W2 = tf.clip_by_norm(gw_W2, clip_bound)
    gw_Wf1 = tf.clip_by_norm(gw_Wf1, clip_bound)
    gw_Wf2 = tf.clip_by_norm(gw_Wf2, clip_bound)

    # sigma = FLAGS.sigma # when comp_eps(lmbda,q,sigma,T,delta)==epsilon

    # sensitivity = 2 * FLAGS.clip_bound #adjacency matrix with one tuple different
    sensitivity = clip_bound  # adjacency matrix with one more tuple

    gw_W1 += tf.random_normal(shape=tf.shape(gw_W1),
                              mean=0.0,
                              stddev=(sigma * sensitivity)**2,
                              dtype=tf.float32)
    gb1 += tf.random_normal(shape=tf.shape(gb1),
                            mean=0.0,
                            stddev=(sigma * sensitivity)**2,
                            dtype=tf.float32)
    gw_W2 += tf.random_normal(shape=tf.shape(gw_W2),
                              mean=0.0,
                              stddev=(sigma * sensitivity)**2,
                              dtype=tf.float32)
    gb2 += tf.random_normal(shape=tf.shape(gb2),
                            mean=0.0,
                            stddev=(sigma * sensitivity)**2,
                            dtype=tf.float32)
    gw_Wf1 += tf.random_normal(shape=tf.shape(gw_Wf1),
                               mean=0.0,
                               stddev=(sigma * sensitivity)**2,
                               dtype=tf.float32)
    gbf1 += tf.random_normal(shape=tf.shape(gbf1),
                             mean=0.0,
                             stddev=(sigma * sensitivity)**2,
                             dtype=tf.float32)
    gw_Wf2 += tf.random_normal(shape=tf.shape(gw_Wf2),
                               mean=0.0,
                               stddev=(sigma * sensitivity)**2,
                               dtype=tf.float32)
    gbf2 += tf.random_normal(shape=tf.shape(gbf2),
                             mean=0.0,
                             stddev=(sigma * sensitivity)**2,
                             dtype=tf.float32)

    train_step = opt.apply_gradients([(gw_W1, W_conv1), (gb1, b_conv1),
                                      (gw_W2, W_conv2), (gb2, b_conv2),
                                      (gw_Wf1, W_fc1), (gbf1, b_fc1),
                                      (gw_Wf2, W_fc2), (gbf2, b_fc2)])

    # craft adversarial samples from x for testing
    #softmax_y_test = tf.nn.softmax(y_conv)

    #====================== attack =========================

    attack_switch = {
        'fgsm': True,
        'ifgsm': True,
        'deepfool': False,
        'mim': True,
        'spsa': False,
        'cwl2': False,
        'madry': True,
        'stm': False
    }

    # define cleverhans abstract models for using cleverhans attacks
    ch_model_logits = CallableModelWrapper(callable_fn=inference,
                                           output_layer='logits')
    ch_model_probs = CallableModelWrapper(callable_fn=inference_prob,
                                          output_layer='probs')

    # define each attack method's tensor
    attack_tensor_dict = {}
    # FastGradientMethod
    if attack_switch['fgsm']:
        print('creating attack tensor of FastGradientMethod')
        fgsm_obj = FastGradientMethod(model=ch_model_probs, sess=sess)
        x_adv_test_fgsm = fgsm_obj.generate(x=x,
                                            eps=fgsm_eps,
                                            clip_min=0.0,
                                            clip_max=1.0)  # testing now
        attack_tensor_dict['fgsm'] = x_adv_test_fgsm

    # Iterative FGSM (BasicIterativeMethod/ProjectedGradientMethod with no random init)
    # default: eps_iter=0.05, nb_iter=10
    if attack_switch['ifgsm']:
        print('creating attack tensor of BasicIterativeMethod')
        ifgsm_obj = BasicIterativeMethod(model=ch_model_probs, sess=sess)
        x_adv_test_ifgsm = ifgsm_obj.generate(x=x,
                                              eps=fgsm_eps,
                                              eps_iter=fgsm_eps / 10,
                                              nb_iter=10,
                                              clip_min=0.0,
                                              clip_max=1.0)
        attack_tensor_dict['ifgsm'] = x_adv_test_ifgsm

    # MomentumIterativeMethod
    # default: eps_iter=0.06, nb_iter=10
    if attack_switch['mim']:
        print('creating attack tensor of MomentumIterativeMethod')
        mim_obj = MomentumIterativeMethod(model=ch_model_probs, sess=sess)
        x_adv_test_mim = mim_obj.generate(x=x,
                                          eps=fgsm_eps,
                                          eps_iter=fgsm_eps / 10,
                                          nb_iter=10,
                                          decay_factor=1.0,
                                          clip_min=0.0,
                                          clip_max=1.0)
        attack_tensor_dict['mim'] = x_adv_test_mim

    # MadryEtAl (Projected Grdient with random init, same as rand+fgsm)
    # default: eps_iter=0.01, nb_iter=40
    if attack_switch['madry']:
        print('creating attack tensor of MadryEtAl')
        madry_obj = MadryEtAl(model=ch_model_probs, sess=sess)
        x_adv_test_madry = madry_obj.generate(x=x,
                                              eps=fgsm_eps,
                                              eps_iter=fgsm_eps / 10,
                                              nb_iter=10,
                                              clip_min=0.0,
                                              clip_max=1.0)
        attack_tensor_dict['madry'] = x_adv_test_madry

    #====================== attack =========================

    #Define the correct prediction and accuracy#
    correct_prediction_x = tf.equal(tf.argmax(y_conv, 1), tf.argmax(y_, 1))
    accuracy_x = tf.reduce_mean(tf.cast(correct_prediction_x, tf.float32))

    correct_prediction = tf.equal(tf.argmax(y_conv, 1), tf.argmax(y_, 1))
    accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

    s = math.log(sqrt(2.0 / math.pi) * 1e+5)
    sigmaEGM = sqrt(2.0) * 1.0 * (sqrt(s) +
                                  sqrt(s + dp_epsilon)) / (2.0 * dp_epsilon)
    print(sigmaEGM)
    __noiseE = np.random.normal(0.0, sigmaEGM**2,
                                28 * 28 * 32).astype(np.float32)
    __noiseE = np.reshape(__noiseE, [-1, 28, 28, 32])

    start_time = time.time()
    logfile = open(_log_filename, 'w')
    last_eval_time = -1
    accum_time = 0
    accum_epoch = 0
    max_benign_acc = -1
    max_adv_acc_dict = {}
    test_size = len(mnist.test.images)
    print("Computing The Noise Redistribution Vector")
    for i in range(4000):
        batch = mnist.train.next_batch(batch_size)
        sess.run([train_step],
                 feed_dict={
                     x: batch[0],
                     y_: batch[1],
                     keep_prob: 0.5,
                     noise: __noiseE * 0
                 })
    batch = mnist.train.next_batch(batch_size * 10)
    grad_redis = sess.run([normalized_grad_r],
                          feed_dict={
                              x: batch[0],
                              y_: batch[1],
                              keep_prob: 1.0,
                              noise: __noiseE * 0
                          })
    #print(grad_redis)
    _sensitivity_2 = sess.run([sensitivity_2],
                              feed_dict={
                                  x: batch[0],
                                  y_: batch[1],
                                  keep_prob: 1.0,
                                  noise: __noiseE * 0
                              })
    #print(_sensitivity_2)

    _sensitivityW = sess.run(sensitivityW)
    #print(_sensitivityW)
    Delta_redis = _sensitivityW / sqrt(_sensitivity_2[0])
    #print(Delta_redis)
    sigmaHGM = sqrt(2.0) * Delta_redis * (sqrt(s) + sqrt(s + dp_epsilon)) / (
        2.0 * dp_epsilon)
    #print(sigmaHGM)
    __noiseH = np.random.normal(0.0, sigmaHGM**2,
                                28 * 28 * 32).astype(np.float32)
    __noiseH = np.reshape(__noiseH, [-1, 28, 28, 32]) * grad_redis

    sess.run(tf.global_variables_initializer())
    print("Training")
    for i in range(num_steps):
        batch = mnist.train.next_batch(batch_size)
        sess.run(
            [train_step],
            feed_dict={
                x: batch[0],
                y_: batch[1],
                keep_prob: 0.5,
                noise: (__noiseE + __noiseH) / 2
            })
        sess.run([privacy_accum_op])
        spent_eps_deltas = priv_accountant.get_privacy_spent(
            sess, target_eps=target_eps)
        if i % 1000 == 0:
            print(i, spent_eps_deltas)
        _break = False
        for _eps, _delta in spent_eps_deltas:
            if _delta >= delta:
                _break = True
                break
        if _break == True:
            break
    print("Testing")
    benign_acc = accuracy_x.eval(
        feed_dict={
            x: mnist.test.images,
            y_: mnist.test.labels,
            keep_prob: 1.0,
            noise: (__noiseE + __noiseH) / 2
        })
    ### PixelDP Robustness ###
    adv_acc_dict = {}
    robust_adv_acc_dict = {}
    robust_adv_utility_dict = {}
    for atk in attack_switch.keys():
        if atk not in adv_acc_dict:
            adv_acc_dict[atk] = -1
            robust_adv_acc_dict[atk] = -1
            robust_adv_utility_dict[atk] = -1

        if attack_switch[atk]:
            adv_images_dict = sess.run(attack_tensor_dict[atk],
                                       feed_dict={
                                           x: mnist.test.images,
                                           y_: mnist.test.labels,
                                           keep_prob: 1.0
                                       })
            #grad_redis = sess.run([normalized_grad_r], feed_dict={x: adv_images_dict, y_: mnist.test.labels, keep_prob: 1.0, noise:__noise})
            ### Robustness ###
            predictions_form_argmax = np.zeros([test_size, 10])
            softmax_predictions = softmax_y.eval(
                feed_dict={
                    x: adv_images_dict,
                    keep_prob: 1.0,
                    noise: (__noiseE + __noiseH) / 2
                })
            argmax_predictions = np.argmax(softmax_predictions, axis=1)
            for n_draws in range(0, 2000):
                if n_draws % 1000 == 0:
                    print(n_draws)
                _noiseE = np.random.normal(0.0, sigmaEGM**2,
                                           28 * 28 * 32).astype(np.float32)
                _noiseE = np.reshape(_noiseE, [-1, 28, 28, 32])
                _noise = np.random.normal(0.0, sigmaHGM**2,
                                          28 * 28 * 32).astype(np.float32)
                _noise = np.reshape(_noise, [-1, 28, 28, 32]) * grad_redis
                for j in range(test_size):
                    pred = argmax_predictions[j]
                    predictions_form_argmax[j, pred] += 1
                softmax_predictions = softmax_y.eval(
                    feed_dict={
                        x: adv_images_dict,
                        keep_prob: 1.0,
                        noise: (__noiseE + __noiseH) / 2 +
                        (_noiseE + _noise) / 4
                    })
                argmax_predictions = np.argmax(softmax_predictions, axis=1)
            final_predictions = predictions_form_argmax
            is_correct = []
            is_robust = []
            for j in range(test_size):
                is_correct.append(
                    np.argmax(mnist.test.labels[j]) == np.argmax(
                        final_predictions[j]))
                robustness_from_argmax = robustnessGGaussian.robustness_size_argmax(
                    counts=predictions_form_argmax[j],
                    eta=0.05,
                    dp_attack_size=fgsm_eps,
                    dp_epsilon=dp_epsilon,
                    dp_delta=1e-5,
                    dp_mechanism='gaussian') / dp_mult
                is_robust.append(robustness_from_argmax >= fgsm_eps)
            adv_acc_dict[atk] = np.sum(is_correct) * 1.0 / test_size
            robust_adv_acc_dict[atk] = np.sum([
                a and b for a, b in zip(is_robust, is_correct)
            ]) * 1.0 / np.sum(is_robust)
            robust_adv_utility_dict[atk] = np.sum(is_robust) * 1.0 / test_size
            print(" {}: {:.4f} {:.4f} {:.4f} {:.4f}".format(
                atk, adv_acc_dict[atk], robust_adv_acc_dict[atk],
                robust_adv_utility_dict[atk],
                robust_adv_acc_dict[atk] * robust_adv_utility_dict[atk]))
            ##############################
    log_str = "step: {}\t target_epsilon: {}\t dp_epsilon: {:.1f}\t attack_norm_bound: {:.1f}\t benign_acc: {:.4f}\t".format(
        i, target_eps, dp_epsilon, attack_norm_bound, benign_acc)
    for atk in attack_switch.keys():
        if attack_switch[atk]:
            log_str += " {}: {:.4f} {:.4f} {:.4f} {:.4f}".format(
                atk, adv_acc_dict[atk], robust_adv_acc_dict[atk],
                robust_adv_utility_dict[atk],
                robust_adv_acc_dict[atk] * robust_adv_utility_dict[atk])
    print(log_str)
    logfile.write(log_str + '\n')
    ##############################
    duration = time.time() - start_time
    logfile.write(str(duration) + '\n')
    logfile.flush()
    logfile.close()
Exemple #9
0
                            config['hist_len']) / num_examples
    print('sampling_probability', sampling_probability)
    rdp = compute_rdp(q=sampling_probability,
                      noise_multiplier=FLAGS.noise_multiplier,
                      steps=steps,
                      orders=orders)
    # Delta is set to 1e-5 because Penn TreeBank has 60000 training points.
    return get_privacy_spent(orders, rdp, target_delta=FLAGS.target_delta)[0]


with tf.Graph().as_default():

    train_op, eval_correct, loss, data_placeholder, label_placeholder, pred = None, None, None, None, None, None

    if FLAGS.dpsgd:
        priv_accountant = accountant.GaussianMomentsAccountant(num_examples)
        gaussian_sanitizer = sanitizer.AmortizedGaussianSanitizer(
            priv_accountant, [FLAGS.l2_norm_clip / batch_size, True])
        # for var in training_params:
        #     if "gradient_l2norm_bound" in training_params[var]:
        #         l2bound = training_params[var]["gradient_l2norm_bound"] / batch_size
        #         gaussian_sanitizer.set_option(var, sanitizer.ClipOption(l2bound, True))

        train_op, eval_correct, loss, data_placeholder, label_placeholder, pred = \
            lstm_inference_dp.lstm_model(oneHot=True, bTrain=True, num_classes=DATA.NUM_CLASSES, num_hidden=config['NUM_LAYERS'], learning_rate=FLAGS.learning_rate, \
                                            dpsgd=True, l2_norm_clip=FLAGS.l2_norm_clip, noise_multiplier=FLAGS.noise_multiplier, \
                                            microbatches=microbatches, num_examples=num_examples)
    else:
        train_op, eval_correct, loss, data_placeholder, label_placeholder, pred = \
            lstm_inference_dp.lstm_model(oneHot=True, bTrain=True, num_classes=DATA.NUM_CLASSES, num_hidden=config['NUM_LAYERS'], learning_rate=FLAGS.learning_rate)