Пример #1
0
    def __init__(self, sess, model, batch_size, confidence, targeted,
                 learning_rate, perturb_window, binary_search_steps,
                 max_iterations, dis_metric, ensemble_size, ground_truth,
                 abort_early, initial_const, clip_min, clip_max,
                 dist_tolerance, num_labels, shape):
        """
        Return a tensor that constructs adversarial examples for the given
        input. Generate uses tf.py_func in order to operate over tensors.

        :param sess: a TF session.
        :param model: a cleverhans.model.Model object.
        :param batch_size: Number of attacks to run simultaneously.
        :param confidence: Confidence of adversarial examples: higher produces
                           examples with larger l2 distortion, but more
                           strongly classified as adversarial.
        :param targeted: boolean controlling the behavior of the adversarial
                         examples produced. If set to False, they will be
                         misclassified in any wrong class. If set to True,
                         they will be misclassified in a chosen target class.
        :param learning_rate: The learning rate for the attack algorithm.
                              Smaller values produce better results but are
                              slower to converge.
        :param binary_search_steps: The number of times we perform binary
                                    search to find the optimal tradeoff-
                                    constant between norm of the purturbation
                                    and confidence of the classification.
        :param max_iterations: The maximum number of iterations. Setting this
                               to a larger value will produce lower distortion
                               results. Using only a few iterations requires
                               a larger learning rate, and will produce larger
                               distortion results.
        :param abort_early: If true, allows early aborts if gradient descent
                            is unable to make progress (i.e., gets stuck in
                            a local minimum).
        :param initial_const: The initial tradeoff-constant to use to tune the
                              relative importance of size of the pururbation
                              and confidence of classification.
                              If binary_search_steps is large, the initial
                              constant is not important. A smaller value of
                              this constant gives lower distortion results.
        :param clip_min: (optional float) Minimum input component value.
        :param clip_max: (optional float) Maximum input component value.
        :param num_labels: the number of classes in the model's output.
        :param shape: the shape of the model's input tensor.
        :param dis_metric: the distance metirc, 1 for l2, 2 for soft-dtw
        """

        self.sess = sess
        self.TARGETED = targeted
        self.LEARNING_RATE = learning_rate
        self.perturb_window = perturb_window
        self.MAX_ITERATIONS = max_iterations
        self.dis_metric = dis_metric
        self.ensemble_size = ensemble_size
        self.BINARY_SEARCH_STEPS = binary_search_steps
        self.ABORT_EARLY = abort_early
        self.CONFIDENCE = confidence
        self.initial_const = initial_const
        self.batch_size = batch_size
        self.dist_tolerance = dist_tolerance
        self.clip_min = clip_min
        self.clip_max = clip_max
        self.model = model
        self.perturb_window = perturb_window
        self.repeat = binary_search_steps >= 10
        self.ground_truth = ground_truth
        self.shape = shape = tuple([batch_size] + list(shape))
        shape_perturb = tuple([batch_size, perturb_window, 1])

        #  self.transform_shape = transform_shape = tuple([transform_batch_size] + list(transform_shape))
        #        self.shape = shape = tuple(list(shape))

        # the variable we're going to optimize over
        modifier = tf.Variable(np.zeros(shape_perturb, dtype=np_dtype))
        tile_times = math.ceil(data_len / perturb_window)
        tile_times_lb = max(math.floor(tile_times / 3), 1)

        # these are variables to be more efficient in sending data to tf
        self.timg = tf.Variable(np.zeros(shape), dtype=tf_dtype, name='timg')
        self.tlab = tf.Variable(np.zeros((batch_size, num_labels)),
                                dtype=tf_dtype,
                                name='tlab')
        self.const = tf.Variable(np.zeros(batch_size),
                                 dtype=tf_dtype,
                                 name='const')

        # and here's what we use to assign them
        self.assign_timg = tf.placeholder(tf_dtype, shape, name='assign_timg')
        self.assign_tlab = tf.placeholder(tf_dtype, (batch_size, num_labels),
                                          name='assign_tlab')
        self.assign_const = tf.placeholder(tf_dtype, [batch_size],
                                           name='assign_const')

        # the resulting instance, tanh'd to keep bounded from clip_min
        # to clip_max
        #        self.newimg = (tf.tanh(modifier + self.timg) + 1) / 2
        #        self.newimg = self.newimg * (clip_max - clip_min) + clip_min
        #self.modifier_tile = tf.tile(modifier, )
        d = tf.expand_dims(tf.constant([0, 0]), axis=0)
        rand_tile_times = tf.random_shuffle(
            tf.range(tile_times_lb, tile_times + 1))
        tile_range = math.floor(tile_times / 2) + 1

        ensemblesize = math.ceil(200 / tile_range)
        for l in range(tile_range):
            rand_times = tf.expand_dims(rand_tile_times[l], axis=0)
            rand_times = tf.concat([tf.constant([1]), rand_times], axis=0)
            rand_times = tf.concat([rand_times, tf.constant([1])], axis=0)
            modifier_tile = tf.tile(modifier, rand_times)
            modifier_shape = tf.shape(modifier_tile)[1]
            b = tf.expand_dims(modifier_shape, axis=0)
            c = tf.concat([tf.constant([0]), data_len - b], axis=0)
            c = tf.expand_dims(c, axis=0)

            c = tf.concat([d, c], axis=0)
            c = tf.concat([c, d], axis=0)

            start_p = tf.cond(tf.equal(modifier_shape, tf.constant(data_len)),
                              lambda: tf.constant(0), lambda: modifier_shape)

            modifier_tile = tf.reshape(tf.pad(modifier_tile, c, "CONSTANT"),
                                       [1, data_len, 1])

            self.newimg = tf.slice(modifier_tile, (0, 0, 0), shape) + self.timg
            if l == 0:
                batch_newdata = EOT_time(modifier_tile, start_p,
                                         ensemblesize) + self.timg
            else:
                batch_newdata = tf.concat([
                    batch_newdata,
                    EOT_time(modifier_tile, start_p, ensemblesize) + self.timg
                ],
                                          axis=0)

        self.batch_newimg = zero_mean(batch_newdata)

        self.loss_batch = model.get_logits(self.batch_newimg)

        self.batch_tlab = tf.tile(self.tlab, (self.batch_newimg.shape[0], 1))

        self.xent = tf.reduce_mean(
            tf.nn.softmax_cross_entropy_with_logits_v2(logits=self.loss_batch,
                                                       labels=self.batch_tlab))

        #self.xent_rest = tf.reduce_mean(
        #    tf.nn.softmax_cross_entropy_with_logits_v2(logits=self.loss_batch_rest, labels=self.batch_tlab_rest))
        self.outputxent = tf.expand_dims(self.xent, 0)
        self.output = tf.expand_dims(tf.reduce_mean(self.loss_batch, axis=0),
                                     0)

        # distance to the input data
        #        self.other = (tf.tanh(self.timg) + 1) / \
        #            2 * (clip_max - clip_min) + clip_min
        #        self.l2dist = reduce_sum(tf.square(self.newimg - self.other),
        #                                 list(range(1, len(shape))))

        if self.dis_metric == 1:
            self.dist = tf.reduce_sum(tf.square(modifier_tile),
                                      list(range(1, len(shape))))
        else:
            if self.dis_metric == 2:
                self.dist = tf.reduce_sum(
                    mysoftdtw(self.timg, modifier_tile, 1) / 9000)
            else:
                _, distvar = tf.nn.moments(tf.multiply(
                    tf.concat([modifier_tile, [[[0.]]]], 1) -
                    tf.concat([[[[0.]]], modifier_tile], 1), Seq1()),
                                           axes=[1])
                self.dist = 10000 * distvar
        #self.l2dist= tf.reduce_sum(mysoftdtw(self.timg, modifier, 1))
        #        self.sdtw = reduce_sum(mysquare_new(self.timg, modifier, 1),list(range(1, len(shape))))

        # compute the probability of the label class versus the maximum other
        #real = tf.reduce_sum((self.tlab) * self.output, 1)
        #other = tf.reduce_max(
        #    (1 - self.tlab) * self.output - self.tlab * 10000,
        #    1)

        #if self.TARGETED:
        # if targeted, optimize for making the other class most likely
        #loss1 = tf.maximum(ZERO(), other - real + self.CONFIDENCE)
        #else:
        # if untargeted, optimize for making this class least likely.
        #loss1 = tf.maximum(ZERO(), real - other + self.CONFIDENCE)

        # sum up the losses
        self.loss2 = tf.reduce_sum(self.dist)
        # self.loss2 = tf.reduce_sum(self.sdtw)
        #self.loss1 = tf.reduce_sum(self.const * (self.xent+self.xent_rest))
        self.loss1 = tf.reduce_sum(self.const * self.xent)
        self.loss = self.loss1 + self.loss2

        # Setup the adam optimizer and keep track of variables we're creating
        start_vars = set(x.name for x in tf.global_variables())
        optimizer = tf.train.AdamOptimizer(self.LEARNING_RATE)
        self.train = optimizer.minimize(self.loss, var_list=[modifier])

        #        tf.summary.scalar('loss', self.loss)
        #        self.train_writer = tf.summary.FileWriter('./log', self.sess.graph)
        #        self.merge = tf.summary.merge_all()

        end_vars = tf.global_variables()
        new_vars = [x for x in end_vars if x.name not in start_vars]

        # these are the variables to initialize when we run
        self.setup = []
        self.setup.append(self.timg.assign(self.assign_timg))
        self.setup.append(self.tlab.assign(self.assign_tlab))
        self.setup.append(self.const.assign(self.assign_const))

        self.init = tf.variables_initializer(var_list=[modifier] + new_vars)
Пример #2
0
    def gradient_descent(self, sess, model):
        def compare(x, y):
            if self.TARGETED:
                return x == y
            else:
                return x != y

        shape = self.shape
        #        self.shape = shape = tuple(list(shape))

        # the variable we're going to optimize over
        modifier = tf.Variable(np.zeros(shape, dtype=np_dtype),
                               name='modifier')

        # these are variables to be more efficient in sending data to tf
        canchange = tf.Variable(np.zeros(shape),
                                dtype=np_dtype,
                                name='canchange')
        simg = tf.Variable(np.zeros(shape), dtype=np_dtype, name='simg')
        original = tf.Variable(np.zeros(shape),
                               dtype=np_dtype,
                               name='original')
        timg = tf.Variable(np.zeros(shape), dtype=np_dtype, name='timg')
        tlab = tf.Variable(np.zeros((self.batch_size, self.num_labels)),
                           dtype=np_dtype,
                           name='tlab')
        const = tf.placeholder(tf.float32, [], name='const')

        # and here's what we use to assign them
        assign_modifier = tf.placeholder(np_dtype,
                                         shape,
                                         name='assign_modifier')
        assign_canchange = tf.placeholder(np_dtype,
                                          shape,
                                          name='assign_canchange')
        assign_simg = tf.placeholder(np_dtype, shape, name='assign_simg')
        assign_original = tf.placeholder(np_dtype,
                                         shape,
                                         name='assign_original')
        assign_timg = tf.placeholder(np_dtype, shape, name='assign_timg')
        assign_tlab = tf.placeholder(np_dtype,
                                     (self.batch_size, self.num_labels),
                                     name='assign_tlab')

        # these are the variables to initialize when we run
        set_modifier = tf.assign(modifier, assign_modifier)
        setup = []
        setup.append(tf.assign(canchange, assign_canchange))
        setup.append(tf.assign(timg, assign_timg))
        setup.append(tf.assign(original, assign_original))
        setup.append(tf.assign(simg, assign_simg))
        setup.append(tf.assign(tlab, assign_tlab))

        # the resulting instance, tanh'd to keep bounded from clip_min to clip_max
        #        self.newimg = (tf.tanh(modifier + self.timg) + 1) / 2
        #        self.newimg = self.newimg * (clip_max - clip_min) + clip_min
        newimg = (modifier + simg) * canchange + (1 - canchange) * original

        # prediction BEFORE-SOFTMAX of the model
        output = model.get_logits(newimg)

        # distance to the input data
        #        self.other = (tf.tanh(self.timg) + 1) / \
        #            2 * (clip_max - clip_min) + clip_min
        #        self.l2dist = reduce_sum(tf.square(self.newimg - self.other),
        #                                 list(range(1, len(shape))))
        #        l2dist = tf.reduce_sum(tf.square(newimg - timg), list(range(1, len(shape))))
        l2dist = mysoftdtw(simg, modifier, 0.1)
        #       l2dist = reduce_sum(mysquare_new(self.timg, modifier, 1),list(range(1, len(shape))))

        # compute the probability of the label class versus the maximum other
        real = tf.reduce_sum((tlab) * output, 1)
        other = tf.reduce_max((1 - tlab) * output - tlab * 10000, 1)

        if self.TARGETED:
            # if targeted, optimize for making the other class most likely
            loss1 = tf.maximum(ZERO(), other - real + self.CONFIDENCE)
        else:
            # if untargeted, optimize for making this class least likely.
            loss1 = tf.maximum(ZERO(), real - other + self.CONFIDENCE)

        # sum up the losses
        loss2 = tf.reduce_sum(l2dist)
        loss = const * loss1 + loss2

        outgrad = tf.gradients(loss, [modifier])[0]

        # Setup the adam optimizer and keep track of variables we're creating
        start_vars = set(x.name for x in tf.global_variables())
        optimizer = tf.train.AdamOptimizer(self.LEARNING_RATE)
        train = optimizer.minimize(loss, var_list=[modifier])
        end_vars = tf.global_variables()
        new_vars = [x for x in end_vars if x.name not in start_vars]

        init = tf.variables_initializer(
            var_list=[modifier, canchange, simg, original, timg, tlab] +
            new_vars)

        def doit(oimgs, labs, starts, valid, CONST):
            imgs = np.array(oimgs)
            starts = np.array(starts)

            sess.run(init)
            sess.run(
                setup, {
                    assign_timg: imgs,
                    assign_tlab: labs,
                    assign_simg: starts,
                    assign_original: oimgs,
                    assign_canchange: valid
                })

            while CONST < self.LARGEST_CONST:
                print('try const', CONST)
                prev = 1e6
                for step in range(self.MAX_ITERATIONS):
                    feed_dict = {const: CONST}

                    #remember the old value
                    oldmodifier = self.sess.run(modifier)

                    if step % (self.MAX_ITERATIONS // 100) == 0:
                        print(step,
                              *sess.run((loss1, loss2), feed_dict=feed_dict))

                    #perform the update step
                    _, l, works, scores = sess.run(
                        [train, loss, loss1, output], feed_dict=feed_dict)

                    if self.ABORT_EARLY and step % (
                        (self.MAX_ITERATIONS // 100) or 1) == 0:
                        if l > prev * .9999:
                            break
                        prev = l

                    if works < 0.0001 and self.ABORT_EARLY:
                        print('loss:', works)
                        self.sess.run(set_modifier,
                                      {assign_modifier: oldmodifier})
                        grads, scores, nimg = sess.run(
                            (outgrad, output, newimg), feed_dict=feed_dict)

                        #                        l2s = np.square(nimg-imgs).sum(axis=(1,2,3))
                        return grads, scores, nimg, CONST

                CONST *= self.const_factor

        return doit
Пример #3
0
a = np.zeros(5)
b = np.array([-1, 1, -1, 1, -1], dtype=np.float64)
l2_ab = np.sum(np.square(b-a))

c = np.array([-np.sqrt(0.5)*2, -np.sqrt(0.5), 0, np.sqrt(0.5), np.sqrt(0.5)*2], dtype=np.float64)
l2_ac = np.sum(np.square(c-a))

from mysoftdtw_c_wd import mysoftdtw
import tensorflow as tf
tmp_a = a.reshape((1, 5, 1))
tmp_a = np.float32(tmp_a)
tmp_b = b.reshape((1, 5, 1))
tmp_b = np.float32(tmp_b)
tmp_c = c.reshape((1, 5, 1))
tmp_c = np.float32(tmp_c)
A = tf.constant(tmp_a)
B = tf.constant(tmp_b)
C = tf.constant(tmp_c)
gamma = tf.constant(0.1, dtype=tf.float32)
Z_ab = mysoftdtw(A, B, gamma)
Z_ac = mysoftdtw(A, C, gamma)
sess = tf.Session()
tf.global_variables_initializer().run(session=sess)
print(Z_ab.eval(session=sess))
print(Z_ac.eval(session=sess))

diff_ab = np.var(np.diff(c-a))
diff_ac = np.var(np.diff(b-a))

plt.plot(a)
plt.plot(b)
Пример #4
0
    def __init__(self, sess, model, batch_size, confidence, targeted,
                 learning_rate, binary_search_steps, max_iterations,
                 abort_early, initial_const, clip_min, clip_max, num_labels,
                 shape):
        """
        Return a tensor that constructs adversarial examples for the given
        input. Generate uses tf.py_func in order to operate over tensors.

        :param sess: a TF session.
        :param model: a cleverhans.model.Model object.
        :param batch_size: Number of attacks to run simultaneously.
        :param confidence: Confidence of adversarial examples: higher produces
                           examples with larger l2 distortion, but more
                           strongly classified as adversarial.
        :param targeted: boolean controlling the behavior of the adversarial
                         examples produced. If set to False, they will be
                         misclassified in any wrong class. If set to True,
                         they will be misclassified in a chosen target class.
        :param learning_rate: The learning rate for the attack algorithm.
                              Smaller values produce better results but are
                              slower to converge.
        :param binary_search_steps: The number of times we perform binary
                                    search to find the optimal tradeoff-
                                    constant between norm of the purturbation
                                    and confidence of the classification.
        :param max_iterations: The maximum number of iterations. Setting this
                               to a larger value will produce lower distortion
                               results. Using only a few iterations requires
                               a larger learning rate, and will produce larger
                               distortion results.
        :param abort_early: If true, allows early aborts if gradient descent
                            is unable to make progress (i.e., gets stuck in
                            a local minimum).
        :param initial_const: The initial tradeoff-constant to use to tune the
                              relative importance of size of the pururbation
                              and confidence of classification.
                              If binary_search_steps is large, the initial
                              constant is not important. A smaller value of
                              this constant gives lower distortion results.
        :param clip_min: (optional float) Minimum input component value.
        :param clip_max: (optional float) Maximum input component value.
        :param num_labels: the number of classes in the model's output.
        :param shape: the shape of the model's input tensor.
        """

        self.sess = sess
        self.TARGETED = targeted
        self.LEARNING_RATE = learning_rate
        self.MAX_ITERATIONS = max_iterations
        self.BINARY_SEARCH_STEPS = binary_search_steps
        self.ABORT_EARLY = abort_early
        self.CONFIDENCE = confidence
        self.initial_const = initial_const
        self.batch_size = batch_size
        self.clip_min = clip_min
        self.clip_max = clip_max
        self.model = model

        self.repeat = binary_search_steps >= 10

        self.shape = shape = tuple([batch_size] + list(shape))
        #        self.shape = shape = tuple(list(shape))

        # the variable we're going to optimize over
        modifier = tf.Variable(np.zeros(shape, dtype=np_dtype))

        # these are variables to be more efficient in sending data to tf
        self.timg = tf.Variable(np.zeros(shape), dtype=tf_dtype, name='timg')
        self.tlab = tf.Variable(np.zeros((batch_size, num_labels)),
                                dtype=tf_dtype,
                                name='tlab')
        self.const = tf.Variable(np.zeros(batch_size),
                                 dtype=tf_dtype,
                                 name='const')

        # and here's what we use to assign them
        self.assign_timg = tf.placeholder(tf_dtype, shape, name='assign_timg')
        self.assign_tlab = tf.placeholder(tf_dtype, (batch_size, num_labels),
                                          name='assign_tlab')
        self.assign_const = tf.placeholder(tf_dtype, [batch_size],
                                           name='assign_const')

        # the resulting instance, tanh'd to keep bounded from clip_min
        # to clip_max
        #        self.newimg = (tf.tanh(modifier + self.timg) + 1) / 2
        #        self.newimg = self.newimg * (clip_max - clip_min) + clip_min
        self.newimg = modifier + self.timg
        data_mean, data_var = tf.nn.moments(self.newimg, axes=1)
        self.newimg = (self.newimg - data_mean) / tf.sqrt(data_var)

        # distance to the input data
        #        self.other = (tf.tanh(self.timg) + 1) / \
        #            2 * (clip_max - clip_min) + clip_min
        #        self.l2dist = reduce_sum(tf.square(self.newimg - self.other),
        #                                 list(range(1, len(shape))))
        # self.l2dist1 = tf.reduce_sum(tf.square(self.newimg - self.timg),list(range(1, len(shape))))
        self.l2dist = mysoftdtw(self.timg, modifier, 0.0001)
        # _, self.l2dist = tf.nn.moments(tf.multiply(tf.concat([modifier, [[[0.]]]], 1) -
        # tf.concat([[[[0.]]], modifier], 1), Seq1()), axes=[1])
        #        self.sdtw = reduce_sum(mysquare_new(self.timg, modifier, 1),list(range(1, len(shape))))

        #        data_mean, data_var = tf.nn.moments(self.newimg, axes=1)
        #        self.newimg = (self.newimg - data_mean)/tf.sqrt(data_var)
        #        self.newimg = tf.stop_gradient(self.newimg)
        # prediction BEFORE-SOFTMAX of the model
        self.output = model.get_logits(self.newimg)

        # compute the probability of the label class versus the maximum other
        real = tf.reduce_sum((self.tlab) * self.output, 1)
        other = tf.reduce_max(
            (1 - self.tlab) * self.output - self.tlab * 10000, 1)

        if self.TARGETED:
            # if targeted, optimize for making the other class most likely
            loss1 = tf.maximum(ZERO(), other - real + self.CONFIDENCE)
        else:
            # if untargeted, optimize for making this class least likely.
            loss1 = tf.maximum(ZERO(), real - other + self.CONFIDENCE)

#        loss1 =  tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits_v2(logits=self.output,labels=self.tlab))

# sum up the losses
#        self.loss3 = tf.reduce_sum(20000*self.loss3)
# self.loss2 = tf.reduce_sum(self.l2dist*10000)
#        self.loss2 = tf.reduce_sum(self.l2dist1)
        self.loss2 = tf.reduce_sum(self.l2dist)
        self.loss1 = tf.reduce_sum(self.const * loss1)
        self.loss = self.loss1 + self.loss2

        # Setup the adam optimizer and keep track of variables we're creating
        start_vars = set(x.name for x in tf.global_variables())
        optimizer = tf.train.AdamOptimizer(self.LEARNING_RATE)
        self.train = optimizer.minimize(self.loss, var_list=[modifier])

        #        tf.summary.scalar('loss', self.loss)
        #        self.train_writer = tf.summary.FileWriter('./log', self.sess.graph)
        #        self.merge = tf.summary.merge_all()

        end_vars = tf.global_variables()
        new_vars = [x for x in end_vars if x.name not in start_vars]

        # these are the variables to initialize when we run
        self.setup = []
        self.setup.append(self.timg.assign(self.assign_timg))
        self.setup.append(self.tlab.assign(self.assign_tlab))
        self.setup.append(self.const.assign(self.assign_const))

        self.init = tf.variables_initializer(var_list=[modifier] + new_vars)