These are chat archives for Snaipe/Criterion

1st
Mar 2016
Dominik
@kaidowei
Mar 01 2016 15:39
@Snaipe so, first draft
don't look at the first macros too closely, they just count the number of VA_ARGS
Franklin Mathieu
@Snaipe
Mar 01 2016 15:46
That's a good start, but tmp_storageassumes that every parameter or return type fit in a pointer type
Dominik
@kaidowei
Mar 01 2016 15:46
with http://stackoverflow.com/questions/1872220/is-it-possible-to-iterate-over-arguments-in-variadic-macros we could even iterate over the va_args and print the right type ins the functions...
Franklin Mathieu
@Snaipe
Mar 01 2016 15:47
I would suggest declaring an internal struct with the __VA_ARGS__
Dominik
@kaidowei
Mar 01 2016 15:47
yeah, that's the next step
what we're doing is essentially generating the mocking functions, but without ruby or that other stuff
opmock uses for example
Franklin Mathieu
@Snaipe
Mar 01 2016 15:49
also, I feel that the API should be mmk_expect(foo, ...) rather than mmk_foo_expect (you can trivially convert the first form to the other form)
and i'm not sure about using "expect" rather than "returns"
or rather now that I think about it it seems a bit too rigid
Dominik
@kaidowei
Mar 01 2016 15:50
well, we expect, that foo is called with the parameters a,b,c and return d
Franklin Mathieu
@Snaipe
Mar 01 2016 15:50
expect shouldn't really define what gets returned, it enforces what gets passed to the stub
you could for instance expect 1, then 2, then anything to be passed, while returning 3, then 4, then 48, then -1, then always 0
the number of expects needn't match the number of returns
Dominik
@kaidowei
Mar 01 2016 15:52
well, the other frameworks assume, that the test-developer knows, how often the function will be called.
Then they can be most strict about the calls.
Franklin Mathieu
@Snaipe
Mar 01 2016 15:52
yes, but that's not what i'm saying
i'm saying that over 4 calls for instance, you could expect the param to be 1, then 2, then 3, then 4
Dominik
@kaidowei
Mar 01 2016 15:53
yes
Franklin Mathieu
@Snaipe
Mar 01 2016 15:53
and define the values to be returned to be 1 the first time, then 2 all the other times
or maybe not, that could be too confusing
Dominik
@kaidowei
Mar 01 2016 15:54
then you need four lines mmk_expect(foo, 1, 1); mmk_expect(foo, 2, 2); mmk_expect(foo, 3, 2); mmk_expect(foo, 4, 2);
Franklin Mathieu
@Snaipe
Mar 01 2016 15:54
yeah, but my main complaint was that the 2 gets repeated
but decoupling might be a bad idea after all
Dominik
@kaidowei
Mar 01 2016 15:55
well, I want to prevent the case, that we expect x calls, but only have y < x return values
Franklin Mathieu
@Snaipe
Mar 01 2016 15:56
hey, even better, since you have control over what gets passed
you could declare a struct wrapper for your expect params
like
struct foo_params {
    void *returning;
    int first;
    double second;
}
(assuming mmk_declare(void*, foo, int first, double second))
Dominik
@kaidowei
Mar 01 2016 15:57
yes, we could do that.
Franklin Mathieu
@Snaipe
Mar 01 2016 15:57
mmk_expect would become something like mmk_expect(foo, .returning = NULL, .first = 1, .second = 42.3)
or mmk_expect(foo, NULL, 1, 42.3)
since both syntaxes are valid
Dominik
@kaidowei
Mar 01 2016 15:58
or mmk_expect(foo, my_foo_struct);
so you can easily add 1000 calls
and have less definitions.
good idea :)
Franklin Mathieu
@Snaipe
Mar 01 2016 15:59
to be fair if you have 1000 calls, you'd wrap it in a for loop
repeated definitions are very unlikely to happen
Dominik
@kaidowei
Mar 01 2016 16:00
sure
my bad, stupid argument, BUT
if you give the struct (or better, a pointer) you can modify that thing after you gave it to the framework
dunno if there really is a case for that, but there might be
Franklin Mathieu
@Snaipe
Mar 01 2016 16:01
you could still add a second function to do this
Dominik
@kaidowei
Mar 01 2016 16:02
right
Franklin Mathieu
@Snaipe
Mar 01 2016 16:03
not sure if that would be a frequent use case, so you could have #define mmk_expect(Name, ...) mmk_bind(Name, &(struct Name ## _params) { __VA_ARGS__ })
and you define mmk_bind to be the function that takes your struct
Dominik
@kaidowei
Mar 01 2016 16:03
yep
to store values, we would need a queue of struct foo_params
Franklin Mathieu
@Snaipe
Mar 01 2016 16:05
just make the structure an intrusive list
so there won't be any dynamic allocation
Dominik
@kaidowei
Mar 01 2016 16:07
right. the "I dont care about the values, just return this" case is not solved yet
and do we support that for some parameter or is it all-or-nothing?
Franklin Mathieu
@Snaipe
Mar 01 2016 16:08
well, if you implement the syntax above, you can simply skip parameters
Dominik
@kaidowei
Mar 01 2016 16:10
which syntax? the mmk_expect?
Franklin Mathieu
@Snaipe
Mar 01 2016 16:10
yes
Dominik
@kaidowei
Mar 01 2016 16:10
even if you just give some parameters, the other will be there... if we're lucky, they're 0
Franklin Mathieu
@Snaipe
Mar 01 2016 16:10
they always are 0
Dominik
@kaidowei
Mar 01 2016 16:11
they are?
Franklin Mathieu
@Snaipe
Mar 01 2016 16:11
designated initializers and compound literals explicitely zero out unspecified fields
Dominik
@kaidowei
Mar 01 2016 16:11
okay :)
but... what if I want the framework to check for 0
Franklin Mathieu
@Snaipe
Mar 01 2016 16:11
yeah, that's an issue
Dominik
@kaidowei
Mar 01 2016 16:11
we cant tell, if the caller wants us not to check or to check against 0
Franklin Mathieu
@Snaipe
Mar 01 2016 16:12
you could experiment with somethink like &(foo_params) { .first = mmk_any, .second = mmk_any, __VA_ARGS__ }
iirc any later field specification override earlier specifications
Dominik
@kaidowei
Mar 01 2016 16:13
we can use some bitfield to tell, when to expect and when to ignore
Franklin Mathieu
@Snaipe
Mar 01 2016 16:13
bitfields aren't portable sadly
Dominik
@kaidowei
Mar 01 2016 16:14
array of bool :D
Franklin Mathieu
@Snaipe
Mar 01 2016 16:14
that would require you to identify what gets passed in your parameter list
i'm not sure that's even possible
or if it's possible, you're going to spend a lot of time fighting with macros
btw, all of this would probably require you to change the prototype of mmk_define, because you'd need to isolate both the type and the name of the parameters
you'd have mmk_define(int, foo, int, param0, int, param1, ...)
which is a bit more unfortunate than the first syntax
but still understandable
Dominik
@kaidowei
Mar 01 2016 16:17
I'm thinking #define mmk_ignore_parameter_1 .ignore[0] = trueand so on for 10+ parameters
or even #define mmk_ignore_parameter(num) .ignore[num -1] = true
Franklin Mathieu
@Snaipe
Mar 01 2016 16:19
that could work
Dominik
@kaidowei
Mar 01 2016 16:19
und ignore_all sets that for the whole array
btw... I'm busy this evening & tomorrow. (except for work :D) do you want to test this out?
Franklin Mathieu
@Snaipe
Mar 01 2016 16:20
I'm currently setting up travis builds, I'll experiment with that on my end after this
Dominik
@kaidowei
Mar 01 2016 16:22
okay
but this is good progress :)
Franklin Mathieu
@Snaipe
Mar 01 2016 16:24
Haha, yes, but we still have a long way to go
Dominik
@kaidowei
Mar 01 2016 16:24
haven't thought about mocking functions, that contain varargs
Franklin Mathieu
@Snaipe
Mar 01 2016 16:24
That's also an issue
we'll probably have to provide functions to build a va_list structure per platform
then pass it to a special .va_args parameter
Dominik
@kaidowei
Mar 01 2016 16:26
let future us deal with that ;)
Franklin Mathieu
@Snaipe
Mar 01 2016 16:27
yeah, that's going to be a pain though
Dominik
@kaidowei
Mar 01 2016 16:27
I'm not sure, other frameworks support that
and the callback approach will work