Example #1
0
 def test_combine_ip_mod2(self):
     """This function tests the inner product mod 2 combiner function with two pairs of input and output."""
     assert_array_equal(
         LTFArray.combiner_ip_mod2(
             array([
                 [1, 1, -3, 1],
                 [-1, -1, -1, 1],
                 [-2, -2, 2, 1]
             ])
         ),
         [
             1,
             -1,
             -4
         ]
     )
     assert_array_equal(
         LTFArray.combiner_ip_mod2(
             array([
                 [1, 1, 1, 1, 1, 1],
                 [-1, -1, -1, 1, -1, -1],
                 [-2, -2, 2, 1, 10, 10]
             ])
         ),
         [
             1,
             1,
             -40
         ]
     )
Example #2
0
    def test_learn_ip_mod2(self):
        """"
        Stupid test which gains code coverage
        """
        instance_prng = RandomState(seed=TestLogisticRegression.seed_instance)
        model_prng = RandomState(seed=TestLogisticRegression.seed_model)

        instance = LTFArray(
            weight_array=LTFArray.normal_weights(
                TestLogisticRegression.n,
                TestLogisticRegression.k,
                random_instance=instance_prng),
            transform=LTFArray.transform_id,
            combiner=LTFArray.combiner_ip_mod2,
        )

        lr_learner = LogisticRegression(
            TrainingSet(instance=instance, N=TestLogisticRegression.N),
            TestLogisticRegression.n,
            TestLogisticRegression.k,
            transformation=LTFArray.transform_id,
            combiner=LTFArray.combiner_xor,
            weights_prng=model_prng,
        )
        lr_learner.learn()
Example #3
0
class Benchmark(Experiment):
    """
    Measures the time LTFArray.eval takes to evaluate a set of inputs.
    """
    def __init__(self, progress_log_prefix, parameters):
        super().__init__(progress_log_prefix, parameters)
        self.set = None
        self.ltf_array = None

    def prepare(self):
        self.set = sample_inputs(self.parameters.n, self.parameters.N,
                                 RandomState(seed=self.parameters.seed_input))
        self.ltf_array = LTFArray(
            weight_array=LTFArray.normal_weights(self.parameters.n,
                                                 self.parameters.k),
            transform=self.parameters.transform,
            combiner=self.parameters.combiner,
        )

    def run(self):
        self.ltf_array.eval(self.set)

    def analyze(self):

        return Result(
            experiment_id=self.id,
            pid=getpid(),
            measured_time=self.measured_time,
        )
Example #4
0
 def prepare(self):
     """
     Initializes the instance, the training set and the learner to then run the logistic regression
     with the given parameters.
     """
     self.instance = LTFArray(
         weight_array=LTFArray.normal_weights(
             self.parameters.n,
             self.parameters.k,
             random_instance=RandomState(
                 seed=self.parameters.seed_instance)),
         transform=self.parameters.transformation,
         combiner=self.parameters.combiner,
     )
     self.learner = LogisticRegression(
         tools.TrainingSet(instance=self.instance,
                           N=self.parameters.N,
                           random_instance=RandomState(
                               self.parameters.seed_challenge)),
         self.parameters.n,
         self.parameters.k,
         transformation=self.instance.transform,
         combiner=self.instance.combiner,
         weights_prng=RandomState(seed=self.parameters.seed_model),
         logger=self.progress_logger,
         minibatch_size=self.parameters.mini_batch_size,
         convergance_decimals=self.parameters.convergence_decimals or 2,
         shuffle=self.parameters.shuffle,
     )
Example #5
0
    def test_training_set_challenges(self):
        """The TrainingSet should generate the same challenges for equal seeds."""
        n = 8
        k = 1
        transformation = LTFArray.transform_id
        combiner = LTFArray.combiner_xor
        N = 1000
        instance_prng = RandomState(0x4EFEA)
        weight_array = LTFArray.normal_weights(n,
                                               k,
                                               random_instance=instance_prng)

        instance = LTFArray(
            weight_array=weight_array,
            transform=transformation,
            combiner=combiner,
        )

        challenge_seed = 0xAB17D

        training_set_1 = TrainingSet(
            instance=instance,
            N=N,
            random_instance=RandomState(challenge_seed))
        training_set_2 = TrainingSet(
            instance=instance,
            N=N,
            random_instance=RandomState(challenge_seed))

        self.assertTrue(
            array_equal(training_set_1.challenges, training_set_2.challenges),
            'The challenges are not equal.',
        )
Example #6
0
def main():
    """
    Run an example how to use pypuf.
    Developers Notice: Changes here need to be mirrored to README!
    """
    
    # create a simulation with random (Gaussian) weights
    # for 64-bit 4-XOR
    instance = LTFArray(
        weight_array=LTFArray.normal_weights(n=64, k=2),
        transform=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor,
    )

    # create the learner
    lr_learner = LogisticRegression(
        t_set=tools.TrainingSet(instance=instance, N=12000),
        n=64,
        k=2,
        transformation=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor,
    )

    # learn and test the model
    model = lr_learner.learn()
    accuracy = 1 - tools.approx_dist(instance, model, 10000)

    # output the result
    print('Learned a 64bit 2-xor XOR Arbiter PUF from 12000 CRPs with accuracy %f' % accuracy)
Example #7
0
    def test_reliability(self):
        """This method tests the test_reliability calculation."""
        n = 8
        k = 8
        N = 2**n
        transformation = LTFArray.transform_id
        combiner = LTFArray.combiner_xor
        instance = LTFArray(
            weight_array=LTFArray.normal_weights(
                n=n, k=k, random_instance=RandomState(0xA1A1)),
            transform=transformation,
            combiner=combiner,
        )
        challenges = sample_inputs(n, N, random_instance=RandomState(0xFAB1A))
        reliabilities = []
        for challenge in challenges:
            reliabilities.append(
                PropertyTest.reliability(instance, reshape(challenge, (1, n))))

        # For noiseless simulations the responses are always the same hence the reliability is 0%
        assert_array_equal(reliabilities, repeat(0.0, N))

        noisy_instance = NoisyLTFArray(
            weight_array=NoisyLTFArray.normal_weights(
                n=n, k=k, random_instance=RandomState(0xA1A1)),
            transform=transformation,
            combiner=combiner,
            sigma_noise=15.0,
            random_instance=RandomState(0x5015E),
        )
        for challenge in challenges:
            reliability = PropertyTest.reliability(noisy_instance,
                                                   reshape(challenge, (1, n)))
            # For noisy simulations the responses should vary
            self.assertNotEqual(reliability, 0.0)
Example #8
0
 def run(self):
     self.instance = LTFArray(weight_array=LTFArray.normal_weights(
         self.n, self.k, random_instance=self.instance_prng),
                              transform=self.transformation,
                              combiner=self.combiner,
                              bias=0.0)
     validation_size = int((self.N / 1.1) // 10)
     self.training_set = TrainingSet(instance=self.instance,
                                     N=self.N - validation_size,
                                     random_instance=self.challenge_prng)
     self.validation_set = TrainingSet(instance=self.instance,
                                       N=validation_size,
                                       random_instance=self.distance_prng)
     self.learner = CorrelationAttack(
         n=self.n,
         k=self.k,
         training_set=self.training_set,
         validation_set=self.validation_set,
         weights_prng=self.model_prng,
         lr_iteration_limit=self.lr_iteration_limit,
         mini_batch_size=self.mini_batch_size,
         convergence_decimals=self.convergence_decimals,
         shuffle=self.shuffle,
         logger=self.progress_logger,
     )
     self.model = self.learner.learn()
Example #9
0
 def test_1_n_bent(self):
     test_array = array([
         [1, -1, -1, 1, -1, 1],
         [-1, 1, 1, -1, -1, 1],
     ])
     assert_array_equal(LTFArray.transform_1_n_bent(test_array, k=3), [
         [
             [1, -1, 1, -1, 1, -1],
             [1, -1, -1, 1, -1, 1],
             [1, -1, -1, 1, -1, 1],
         ],
         [
             [1, -1, 1, -1, 1, -1],
             [-1, 1, 1, -1, -1, 1],
             [-1, 1, 1, -1, -1, 1],
         ],
     ])
     test_array = array([
         [1, -1, -1, 1, -1, 1],
         [-1, 1, 1, -1, -1, 1],
     ])
     assert_array_equal(LTFArray.transform_1_n_bent(test_array, k=1), [
         [
             [1, -1, 1, -1, 1, -1],
         ],
         [
             [1, -1, 1, -1, 1, -1],
         ],
     ])
Example #10
0
    def test_uniqueness_set(self):
        """This method tests the uniqueness set generation function."""
        n = 8
        k = 1
        N = 2**n
        instance_count = 25
        measurements = 2
        transformation = LTFArray.transform_id
        combiner = LTFArray.combiner_xor
        instances = [
            LTFArray(weight_array=LTFArray.normal_weights(
                n=n, k=k, random_instance=RandomState(0xA1A1 + i)),
                     transform=transformation,
                     combiner=combiner) for i in range(instance_count)
        ]
        challenges = sample_inputs(n, N, random_instance=RandomState(0xFAB10))

        uniqueness_set = PropertyTest.uniqueness_set(instances,
                                                     challenges,
                                                     measurements=measurements)

        # Check uniqueness_set to have the expected number of elements
        self.assertEqual(len(uniqueness_set), N * measurements)
        # For normal distributed weights is the expected uniqueness near 0.5
        self.assertEqual(round(mean(uniqueness_set), 1), 0.5)
Example #11
0
def pipeline(N):
    instance = LTFArray(
        weight_array=LTFArray.normal_weights(n=64, k=2),
        transform=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor
    )

    train_set = tools.TrainingSet(instance=instance, N=N)

    train_size = int(len(train_set.challenges) * 0.95)

    val_set = train_set.subset(slice(train_size, None))
    train_set = train_set.subset(slice(None, train_size))
    
    lr_learner = LogisticRegression(
        t_set=train_set,
        n=64,
        k=2,
        transformation=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor,
    )

    model = lr_learner.learn()
    
    val_set_predicted_responses = model.eval(val_set.challenges)

    accuracy = accuracy_score(val_set_predicted_responses, val_set.responses)
    
    return accuracy
Example #12
0
 def prepare(self):
     self.set = sample_inputs(self.parameters.n, self.parameters.N,
                              RandomState(seed=self.parameters.seed_input))
     self.ltf_array = LTFArray(
         weight_array=LTFArray.normal_weights(self.parameters.n,
                                              self.parameters.k),
         transform=self.parameters.transform,
         combiner=self.parameters.combiner,
     )
Example #13
0
    def learn(self):
        """
        Compute a model according to the given LTF Array parameters and training set.
        Note that this function can take long to return.
        :return: pypuf.simulation.arbiter_based.LTFArray
                 The computed model.
        """

        # log format
        def log_state():
            """
            This method is used to log a snapshot of learning variables while running.
            """
            if self.logger is None:
                return
            self.logger.debug(
                '%i\t%f\t%f\t%s' %
                (self.iteration_count, distance, norm(updater.step), ','.join(
                    map(str, model.weight_array.flatten()))))

        # let numpy raise exceptions
        seterr(all='raise')

        # we start with a random model
        model = LTFArray(
            weight_array=LTFArray.normal_weights(self.n, self.k,
                                                 self.weights_mu,
                                                 self.weights_sigma,
                                                 self.weights_prng),
            transform=self.transformation,
            combiner=self.combiner,
        )

        updater = self.RPropModelUpdate(model)
        converged = False
        distance = 1
        self.iteration_count = 0
        log_state()
        while not converged and self.iteration_count < self.iteration_limit:
            self.iteration_count += 1

            # compute gradient & update model
            gradient = self.gradient(model)
            model.weight_array += updater.update(gradient)

            # check convergence
            converged = norm(updater.step) < 10**-self.convergence_decimals

            # log
            log_state()

        if not converged:
            self.converged = False
        else:
            self.converged = True

        return model
Example #14
0
 def test_combine_ip_mod2(self):
     assert_array_equal(
         LTFArray.combiner_ip_mod2(
             array([[1, 1, -3, 1], [-1, -1, -1, 1], [-2, -2, 2, 1]])),
         [1, -1, -4])
     assert_array_equal(
         LTFArray.combiner_ip_mod2(
             array([[1, 1, 1, 1, 1, 1], [-1, -1, -1, 1, -1, -1],
                    [-2, -2, 2, 1, 10, 10]])), [1, 1, -40])
Example #15
0
    def test_majority_voting(self):
        """This method is used to test if majority vote works.
        The first test checks for unequal PUF responses with a LTFArray without noise and a SimulationMajorityLTFArray
        instance with noise. The second test checks if majority voting works and the instance with and without noise
        generate equal resonses.
        """
        weight_prng1 = RandomState(seed=0xBADA55)
        noise_prng = RandomState(seed=0xC0FFEE)
        crp_count = 16  # number of random inputs per test set
        n = 8
        k = 16
        mu = 0
        sigma = 1
        vote_count = 1

        weight_array = LTFArray.normal_weights(n, k, mu, sigma, weight_prng1)

        mv_noisy_ltf_array = SimulationMajorityLTFArray(
            weight_array=weight_array,
            transform=LTFArray.transform_id,
            combiner=LTFArray.combiner_xor,
            sigma_noise=1,
            random_instance_noise=noise_prng,
            vote_count=vote_count,
        )

        ltf_array = LTFArray(weight_array=weight_array,
                             transform=LTFArray.transform_id,
                             combiner=LTFArray.combiner_xor)

        inputs = tools.random_inputs(
            n, crp_count, random_instance=RandomState(seed=0xDEADDA7A))

        ltf_array_result = ltf_array.eval(inputs)
        mv_noisy_ltf_array_result = mv_noisy_ltf_array.eval(inputs)
        # These test checks if the output is different because of noise
        self.assertFalse(
            array_equal(ltf_array_result, mv_noisy_ltf_array_result),
            'These arrays must be different')

        # reset pseudo random number generator
        noise_prng = RandomState(seed=0xC0FFEE)
        # increase the vote_count in order to get equality
        vote_count = 2845
        mv_noisy_ltf_array = SimulationMajorityLTFArray(
            weight_array=weight_array,
            transform=LTFArray.transform_id,
            combiner=LTFArray.combiner_xor,
            sigma_noise=1,
            random_instance_noise=noise_prng,
            vote_count=vote_count,
        )
        # This checks if the majority vote works
        mv_noisy_ltf_array_result = mv_noisy_ltf_array.eval(inputs)
        assert_array_equal(mv_noisy_ltf_array_result, ltf_array_result)
Example #16
0
    def test_majority_voting(self):
        weight_prng1 = RandomState(seed=0xBADA55)
        noise_prng = RandomState(seed=0xC0FFEE)
        crp_count = 16  # number of random inputs per test set
        n = 8
        k = 16
        mu = 0
        sigma = 1
        vote_count = 1

        weight_array = LTFArray.normal_weights(n, k, mu, sigma, weight_prng1)

        mv_noisy_ltf_array = SimulationMajorityLTFArray(
            weight_array=weight_array,
            transform=LTFArray.transform_id,
            combiner=LTFArray.combiner_xor,
            sigma_noise=1,
            random_instance_noise=noise_prng,
            vote_count=vote_count,
        )

        ltf_array = LTFArray(weight_array=weight_array,
                             transform=LTFArray.transform_id,
                             combiner=LTFArray.combiner_xor)

        inputs = array(
            list(
                tools.random_inputs(
                    n, crp_count,
                    random_instance=RandomState(seed=0xDEADDA7A))))

        ltf_array_result = ltf_array.eval(inputs)
        mv_noisy_ltf_array_result = mv_noisy_ltf_array.eval(inputs)
        # These test checks if the output is different because of noise
        self.assertFalse(
            array_equal(ltf_array_result, mv_noisy_ltf_array_result),
            'These arrays must be different')

        # reset pseudo random number generator
        noise_prng = RandomState(seed=0xC0FFEE)
        # increase the vote_count in order to get equality
        vote_count = 277
        mv_noisy_ltf_array = SimulationMajorityLTFArray(
            weight_array=weight_array,
            transform=LTFArray.transform_id,
            combiner=LTFArray.combiner_xor,
            sigma_noise=1,
            random_instance_noise=noise_prng,
            vote_count=vote_count,
        )
        # This checks if the majority vote works
        mv_noisy_ltf_array_result = mv_noisy_ltf_array.eval(inputs)
        assert_array_equal(mv_noisy_ltf_array_result, ltf_array_result)
Example #17
0
 def test_shift(self):
     """This method tests the shift transformation with predefined input and output."""
     test_array = array([
         [-1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, 2, 3, 4, 5],
     ],
                        dtype=tools.BIT_TYPE)
     assert_array_equal(LTFArray.transform_shift(test_array, k=3), [[
         [-1, 1, 1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
     ], [
         [-1, -1, -1, -1, -1],
         [-1, -1, -1, -1, -1],
         [-1, -1, -1, -1, -1],
     ], [
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
         [-1, -1, -1, 1, 1],
     ], [
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
         [-1, -1, -1, 1, 1],
     ], [
         [1, 2, 3, 4, 5],
         [2, 3, 4, 5, 1],
         [3, 4, 5, 1, 2],
     ]])
Example #18
0
    def test_transformations_combiner(self):
        """
        This test checks all combinations of transformations and combiners for SimulationMajorityLTFArray to run.
        """
        noise_prng = RandomState(seed=0xC0FFEE)
        weight_prng1 = RandomState(seed=0xBADA55)
        crp_count = 16  # number of random inputs per test set
        n = 64
        k = 2
        mu = 0
        sigma = 1
        vote_count = 1
        weight_array = LTFArray.normal_weights(n, k, mu, sigma, weight_prng1)

        inputs = tools.random_inputs(
            n, crp_count, random_instance=RandomState(seed=0xDEADDA7A))

        combiners = get_functions_with_prefix('combiner_',
                                              SimulationMajorityLTFArray)
        transformations = get_functions_with_prefix(
            'transform_', SimulationMajorityLTFArray)

        for transformation in transformations:
            for combiner in combiners:
                mv_noisy_ltf_array = SimulationMajorityLTFArray(
                    weight_array=weight_array,
                    transform=transformation,
                    combiner=combiner,
                    sigma_noise=1,
                    random_instance_noise=noise_prng,
                    vote_count=vote_count,
                )
                mv_noisy_ltf_array.eval(inputs)
Example #19
0
 def test_id(self):
     """
     This method test the identity function for the predefined inputs (challenges). If every challenge is duplicated
     k times the function works correct.
     """
     test_challenges = array([[
         [-1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [1, 1, -1, -1, -1],
     ], [
         [1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [-1, 1, -1, -1, -1],
     ], [
         [-1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [-1, 1, -1, -1, -1],
     ]],
                             dtype=tools.BIT_TYPE)
     for challenges in test_challenges:
         assert_array_equal(
             LTFArray.transform_id(challenges, k=4),
             [[challenges[0], challenges[0], challenges[0], challenges[0]],
              [challenges[1], challenges[1], challenges[1], challenges[1]],
              [challenges[2], challenges[2], challenges[2], challenges[2]]])
Example #20
0
 def test_generate_stacked_transform(self):
     """
     This method tests the stacked transformation generation of identity and shift with predefined input and output.
     """
     test_array = array([
         [1, -1, 1, -1],
         [-1, -1, 1, -1],
     ],
                        dtype=tools.BIT_TYPE)
     assert_array_equal(
         LTFArray.generate_stacked_transform(
             transform_1=LTFArray.transform_id,
             puf_count=2,
             transform_2=LTFArray.transform_shift)(test_array, k=4), [
                 [
                     [1, -1, 1, -1],
                     [1, -1, 1, -1],
                     [1, -1, 1, -1],
                     [-1, 1, -1, 1],
                 ],
                 [
                     [-1, -1, 1, -1],
                     [-1, -1, 1, -1],
                     [-1, -1, 1, -1],
                     [-1, 1, -1, -1],
                 ],
             ])
Example #21
0
def train(challenges, responses, t_pairs):
    try:
        with open('weights.txt', 'rb') as f:
            weights = np.load(f)
    except:
        print("[*] ENOWEIGHTS")

    # create instance frome same weights for accuracy calculation
    instance = LTFArray(
        weight_array=weights,
        transform=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor,
    )

    # train model from obtained CRPs
    training_set = tools.ChallengeResponseSet(challenges, responses)
    lr_learner = LogisticRegression(
        t_set=training_set,
        n=48,
        k=4,
        transformation=LTFArray.transform_atf,
        combiner=LTFArray.combiner_xor,
    )

    # learn and test the model
    model = lr_learner.learn()
    accuracy = 1 - tools.approx_dist(instance, model, 10000)

    print('Learned a 48-bit 4-xor XOR Arbiter PUF from {} CRPs with accuracy {}'.format(t_pairs, accuracy))
    
    return model
Example #22
0
    def test_parse_file(self):
        """This method checks reading challenge-response pairs from a file."""
        n, k, N = 128, 1, 10
        instance = LTFArray(LTFArray.normal_weights(n, k),
                            LTFArray.transform_atf, LTFArray.combiner_xor)
        original = TrainingSet(instance, N)

        f = NamedTemporaryFile('w')
        for vals in column_stack((original.challenges, original.responses)):
            f.write(' '.join(map(str, vals)) + '\n')
        f.flush()

        loaded = parse_file(f.name, n, in_11_notation=True)
        assert_array_equal(original.challenges, loaded.challenges)
        assert_array_equal(original.responses, loaded.responses)
        f.close()
Example #23
0
 def test_polynomial(self):
     """This method tests the polynomial transformation with predefined input and output for k=4 PUFs."""
     test_array = array([
         [-1, -1, 1, 1, 1, -1, 1, -1, -1, -1, -1, -1, -1, 1, 1, 1, 1,
          1, 1, -1, 1, -1, -1, 1, 1, -1, 1, -1, -1, 1, -1, 1, 1, 1,
          1, 1, -1, 1, 1, 1, 1, 1, -1, 1, 1, 1, 1, 1, -1, 1, -1,
          1, -1, -1, -1, 1, 1, 1, -1, 1, 1, -1, 1, 1]
     ])
     assert_array_equal(
         LTFArray.transform_polynomial(test_array, k=4),
         [
             [
                 [-1, 1, 1, -1, -1, -1, 1, -1, -1, -1, -1, 1, -1, 1, -1, -1, 1, 1, 1, 1, 1, 1, -1, 1,
                  -1, 1, -1, 1, -1, 1, -1, 1, -1, -1, -1, 1, -1, -1, -1, -1, 1, 1, -1, 1, 1, 1, -1, 1,
                  -1, -1, 1, 1, 1, 1, -1, 1, -1, 1, -1, -1, -1, -1, 1, -1],
                 [-1, -1, 1, -1, 1, 1, 1, 1, -1, 1, 1, 1, -1, 1, -1, -1, -1, -1, 1, 1, 1, -1, 1, -1,
                  -1, -1, -1, -1, 1, -1, -1, 1, 1, -1, -1, 1, -1, -1, -1, -1, -1, 1, -1, -1, 1, 1, -1, -1,
                  -1, 1, -1, -1, 1, 1, 1, 1, -1, -1, 1, -1, -1, 1, 1, -1],
                 [-1, 1, 1, 1, 1, -1, 1, 1, 1, 1, -1, -1, -1, 1, 1, -1, 1, 1, 1, -1, -1, -1, -1, -1,
                  1, 1, 1, -1, -1, -1, -1, 1, -1, -1, -1, -1, -1, 1, -1, 1, -1, 1, -1, 1, -1, 1, 1, -1,
                  -1, 1, 1, 1, 1, -1, 1, -1, 1, 1, -1, 1, 1, -1, -1, -1],
                 [1, 1, 1, 1, -1, 1, -1, 1, 1, 1, 1, 1, 1, 1, -1, -1, 1, 1, 1, 1, 1, 1, 1, 1,
                  -1, -1, -1, 1, -1, -1, -1, -1, -1, -1, 1, -1, -1, -1, 1, 1, -1, -1, -1, 1, 1, 1, -1, -1,
                  1, -1, 1, 1, 1, -1, -1, -1, -1, 1, -1, -1, 1, -1, 1, 1]
             ]
         ]
     )
Example #24
0
 def test_shift(self):
     test_array = array([
         [-1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, 2, 3, 4, 5],
     ])
     assert_array_equal(LTFArray.transform_shift(test_array, k=3), [[
         [-1, 1, 1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
     ], [
         [-1, -1, -1, -1, -1],
         [-1, -1, -1, -1, -1],
         [-1, -1, -1, -1, -1],
     ], [
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
         [-1, -1, -1, 1, 1],
     ], [
         [1, 1, -1, -1, -1],
         [1, -1, -1, -1, 1],
         [-1, -1, -1, 1, 1],
     ], [
         [1, 2, 3, 4, 5],
         [2, 3, 4, 5, 1],
         [3, 4, 5, 1, 2],
     ]])
Example #25
0
 def test_atf(self):
     test_array = array([
         [-1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [1, 1, -1, -1, -1],
         [1, 1, 1, -1, -1],
         [-1, -1, -1, -1, -1],
         [-1, 1, -1, -1, -1],
     ])
     assert_array_equal(LTFArray.transform_atf(test_array, k=3), [[
         [-1, 1, 1, 1, -1],
         [-1, 1, 1, 1, -1],
         [-1, 1, 1, 1, -1],
     ], [
         [-1, 1, -1, 1, -1],
         [-1, 1, -1, 1, -1],
         [-1, 1, -1, 1, -1],
     ], [
         [-1, -1, -1, 1, -1],
         [-1, -1, -1, 1, -1],
         [-1, -1, -1, 1, -1],
     ], [
         [1, 1, 1, 1, -1],
         [1, 1, 1, 1, -1],
         [1, 1, 1, 1, -1],
     ], [
         [-1, 1, -1, 1, -1],
         [-1, 1, -1, 1, -1],
         [-1, 1, -1, 1, -1],
     ], [
         [1, -1, -1, 1, -1],
         [1, -1, -1, 1, -1],
         [1, -1, -1, 1, -1],
     ]])
Example #26
0
    def test_reliability_statistic(self):
        """This method tests the reliability statistic of an instance set."""
        n = 8
        k = 1
        N = 2**n
        instance_count = 2
        measurements = 100
        transformation = LTFArray.transform_id
        combiner = LTFArray.combiner_xor

        instances = [
            LTFArray(weight_array=LTFArray.normal_weights(
                n=n, k=k, random_instance=RandomState(0xA1A1 + i)),
                     transform=transformation,
                     combiner=combiner) for i in range(instance_count)
        ]

        challenges = sample_inputs(n, N, random_instance=RandomState(0xFAB10))

        property_test = PropertyTest(instances)
        reliability_statistic = property_test.reliability_statistic(
            challenges, measurements=measurements)
        # For an noiseless set of simulations the reliability must be 0%
        for key, value in reliability_statistic.items():
            if key == 'sv':
                self.assertEqual(value, 0.0, '{}'.format(key))
            elif key == 'samples':
                self.assertEqual(len(value), instance_count * N,
                                 '{}'.format(key))
            else:
                self.assertEqual(value, 0.0, '{}'.format(key))

        noisy_instances = [
            NoisyLTFArray(
                weight_array=LTFArray.normal_weights(
                    n=n, k=k, random_instance=RandomState(0xA1A1 + i)),
                transform=transformation,
                combiner=combiner,
                sigma_noise=0.5,
                random_instance=RandomState(0xCABE),
            ) for i in range(instance_count)
        ]

        noisy_property_test = PropertyTest(noisy_instances)
        noisy_reliability_statistic = noisy_property_test.reliability_statistic(
            challenges, measurements=measurements)
        self.assertNotEqual(noisy_reliability_statistic['mean'], 0.0)
Example #27
0
 def test_generate_random_permutations(self):
     """This method tests the random permutation transformation generation ith predefined inputs and outputs."""
     test_array = array([
         [1, 2, 3, 4],
         [5, 6, 2, 1],
     ],
                        dtype=tools.BIT_TYPE)
     assert_array_equal(
         LTFArray.generate_random_permutation_transform(
             seed=0xbeef,
             nn=4,
             kk=3,
         )(test_array, k=3),
         [
             [
                 [4, 1, 2, 3],
                 [1, 4, 3, 2],
                 [3, 1, 4, 2],
             ],
             [
                 [1, 5, 6, 2],
                 [5, 1, 2, 6],
                 [2, 5, 1, 6],
             ],
         ],
     )
     assert_array_equal(
         LTFArray.generate_random_permutation_transform(
             seed=0xbeef,
             nn=4,
             kk=3,
             atf=True,
         )(test_array, k=3),
         [
             [
                 [4 * 1 * 2 * 3, 1 * 2 * 3, 2 * 3, 3],
                 [1 * 4 * 3 * 2, 4 * 3 * 2, 3 * 2, 2],
                 [3 * 1 * 4 * 2, 1 * 4 * 2, 4 * 2, 2],
             ],
             [
                 [1 * 5 * 6 * 2, 5 * 6 * 2, 6 * 2, 2],
                 [5 * 1 * 2 * 6, 1 * 2 * 6, 2 * 6, 6],
                 [2 * 5 * 1 * 6, 5 * 1 * 6, 1 * 6, 6],
             ],
         ],
     )
Example #28
0
 def test_random_weights(self):
     for test_parameters in self.test_set:
         n = test_parameters[0]
         k = test_parameters[1]
         mu = test_parameters[2]
         sigma = test_parameters[3]
         self.assertTupleEqual(
             shape(LTFArray.normal_weights(n, k, mu, sigma)), (k, n))
Example #29
0
 def test_generate_random_permutations(self):
     """This method tests the random permutation transformation generation ith predefined inputs and outputs."""
     test_array = array([
         [1, 2, 3, 4],
         [10, 20, 30, 40],
     ])
     assert_array_equal(
         LTFArray.generate_random_permutation_transform(
             seed=0xbeef,
             challenge_length=4,
             puf_count=3,
         )(test_array, k=3),
         [
             [
                 [4, 1, 2, 3],
                 [1, 4, 3, 2],
                 [3, 1, 4, 2],
             ],
             [
                 [40, 10, 20, 30],
                 [10, 40, 30, 20],
                 [30, 10, 40, 20],
             ],
         ],
     )
     assert_array_equal(
         LTFArray.generate_random_permutation_transform(
             seed=0xbeef,
             challenge_length=4,
             puf_count=3,
             atf=True,
         )(test_array, k=3),
         [
             [
                 [4 * 1 * 2 * 3, 1 * 2 * 3, 2 * 3, 3],
                 [1 * 4 * 3 * 2, 4 * 3 * 2, 3 * 2, 2],
                 [3 * 1 * 4 * 2, 1 * 4 * 2, 4 * 2, 2],
             ],
             [
                 [40 * 10 * 20 * 30, 10 * 20 * 30, 20 * 30, 30],
                 [10 * 40 * 30 * 20, 40 * 30 * 20, 30 * 20, 20],
                 [30 * 10 * 40 * 20, 10 * 40 * 20, 40 * 20, 20],
             ],
         ],
     )
Example #30
0
    def test_ltf_eval(self):
        """
        Test ltf_eval for correct evaluation of LTFs.
        """

        N = 100  # number of random inputs per test set

        def ltf_eval_slow(challenge, weights):
            """
            evaluate a single challenge with a single ltf specified by weights
            """
            assert len(challenge) == len(weights) - 1
            return dot(challenge,
                       weights[:n]) + weights[n]  # weights[n] is the bias

        for test_parameters in self.test_set:
            n = test_parameters[0]
            k = test_parameters[1]
            mu = test_parameters[2]
            sigma = test_parameters[3]

            inputs = tools.random_inputs(n,
                                         N,
                                         random_instance=RandomState(0xA1))

            ltf_array = LTFArray(
                weight_array=LTFArray.normal_weights(n, k, mu, sigma),
                transform=LTFArray.transform_id,
                combiner=LTFArray.combiner_xor,
            )

            fast_evaluation_result = around(ltf_array.ltf_eval(
                LTFArray.transform_id(inputs, k)),
                                            decimals=8)
            slow_evaluation_result = []
            for challenge in inputs:
                slow_evaluation_result.append([
                    ltf_eval_slow(challenge, ltf_array.weight_array[l])
                    for l in range(k)
                ])
            slow_evaluation_result = around(slow_evaluation_result, decimals=8)

            self.assertTupleEqual(shape(slow_evaluation_result), (N, k))
            self.assertTupleEqual(shape(fast_evaluation_result), (N, k))
            assert_array_equal(slow_evaluation_result, fast_evaluation_result)