Example #1
0
        public AbstractImageSpec WitnessCompose_BottomParam(GrammarRule rule, AbstractImageSpec spec, AbstractImageSpec topSpec)
        {
            Program.DEBUG("Entered WitnessCompose_BottomParam");
            var result = new Dictionary <State, object>();

            foreach (var example in spec.AbstractImageExamples)
            {
                State inputState = example.Key;
                var   output     = example.Value as AbstractImage;
                if (output.isEmptySet())
                {
                    Program.DEBUG("null from WitnessCompose_BottomParam --> output.isEmptySet()");
                    return(null);
                }
                AbstractImage top_image = (AbstractImage)topSpec.AbstractImageExamples[inputState];
                // TODO: Handle different dimensions for bottom_preimage, currently we assume output is proper dimension
                AbstractImage bottom_preimage = new AbstractImage(output.x, output.y, output.w, output.h);
                for (int ay = bottom_preimage.y; ay < bottom_preimage.y + bottom_preimage.h; ay++)
                {
                    for (int ax = bottom_preimage.x; ax < bottom_preimage.x + bottom_preimage.w; ax++)
                    {
                        AbstractValue output_ab_val = output.getAbstractValueAtPixel(ax, ay);
                        if (top_image.InBounds(ax, ay)) // Checking that the x and y coords are in the bounds for top_image
                        {
                            AbstractValue top_image_ab_val = output.getAbstractValueAtPixel(ax, ay);
                            // If either the top_image or the output images allowed no values (not even 0), then return null
                            // as we've entered an invalid state
                            if (top_image_ab_val.IsEmpty() || output_ab_val.IsEmpty())
                            {
                                Program.DEBUG("null from WitnessCompose_BottomParam --> top or output contained no valid values");
                                return(null);
                            }
                            // Check if we ONLY allow 0 on output (HammingWeight is the # of 1 bits in our inner representation)
                            if (output_ab_val.Allows(0) && output_ab_val.HammingWeight() == 1)
                            {
                                // If the top_image doesn't allow 0, this is impossible. Return null
                                if (!top_image_ab_val.Allows(0))
                                {
                                    Program.DEBUG("null from WitnessCompose_BottomParam --> top image didn't allow 0");
                                    return(null);
                                }
                                // if it allows 0 and no other values, that's good, just return 0 for bottom
                                else if (top_image_ab_val.HammingWeight() >= 1)
                                {
                                    bottom_preimage.setAbstractValueAtPixel(ax, ay,
                                                                            new AbstractValue(AbstractConstants.ZERO));
                                }
                                else
                                {
                                    throw new Exception("WitnessCompose_BottomParam --> This shouldn't happen");
                                }
                            }
                            // output is ONLY nonzeros
                            else if (!output_ab_val.Allows(0) && output_ab_val.HammingWeight() >= 1)
                            {
                                // If the top_image doesn't allow 0, that's cool.
                                // It means that our bottom_preimage can contain literally anything
                                // since its contents will be completely ignored
                                if (!top_image_ab_val.Allows(0))
                                {
                                    bottom_preimage.setAbstractValueAtPixel(ax, ay,
                                                                            new AbstractValue(AbstractConstants.ANY));
                                }
                                // otherwise, if top image does allow 0, our bottom preimage
                                // can take on the union of top_image's nonzero values and
                                // the values in output
                                // Example:
                                // output: [1,2,3]
                                // top: [0,1]
                                // bottom: [1,2,3]
                                else
                                {
                                    // First, sanity check! Ensure the nonzero elements of top
                                    // are contained within output, otherwise that's bad and we return null
                                    AbstractValue nonzero_top_image_ab_vals = AbstractValue.Intersect(
                                        new AbstractValue(AbstractConstants.NONZERO),
                                        top_image_ab_val
                                        );
                                    if (!output_ab_val.ContainsAllColors(nonzero_top_image_ab_vals))
                                    {
                                        Program.DEBUG("null from WitnessCompose_BottomParam --> output val wasn't superset of nonzero top vals");
                                        return(null);
                                    }
                                    // Now, easy-peasy, just set bottom_preimage to output
                                    bottom_preimage.setAbstractValueAtPixel(ax, ay, new AbstractValue(output_ab_val.d));
                                }
                            }
                            // output contains nonzero AND allows 0
                            else if (output_ab_val.Allows(0) && output_ab_val.HammingWeight() > 1)
                            {
                                // If the top_image doesn't allow 0, that's bad!
                                // means we can't get 0 on output, so return null
                                if (!top_image_ab_val.Allows(0))
                                {
                                    Program.DEBUG("null from WitnessCompose_BottomParam --> top image didn't allow 0, which is impossible given output accepts zero (and some other nonzeros)");
                                    return(null);
                                }
                                // otherwise, if top image does allow 0, our bottom preimage
                                // can take on the union of top_image's nonzero values and
                                // the nonzero values in output
                                // Example:
                                // output: [0,1,2,3]
                                // top: [0,1]
                                // bottom: [1,2,3]
                                else
                                {
                                    // First, sanity check! Ensure the nonzero elements of top
                                    // are contained within nonzero els of output, otherwise that's bad and we return null
                                    AbstractValue nonzero_top_image_ab_vals = AbstractValue.Intersect(
                                        new AbstractValue(AbstractConstants.NONZERO),
                                        top_image_ab_val
                                        );
                                    AbstractValue nonzero_output_ab_vals = AbstractValue.Intersect(
                                        new AbstractValue(AbstractConstants.NONZERO),
                                        output_ab_val
                                        );
                                    if (!nonzero_output_ab_vals.ContainsAllColors(nonzero_top_image_ab_vals))
                                    {
                                        Program.DEBUG("null from WitnessCompose_BottomParam --> nonzero output val wasn't superset of nonzero top vals");
                                        return(null);
                                    }
                                    // Now, easy-peasy, just set bottom_preimage to (nonzero elements) of output
                                    bottom_preimage.setAbstractValueAtPixel(ax, ay, new AbstractValue(nonzero_output_ab_vals.d));
                                }
                            }
                            else
                            {
                                throw new Exception("We should not have thrown this. Check WitnessCompose_BottomParam.");
                            }
                        }
                        else
                        {
                            // TODO: Determine if we want to support this?
                            bottom_preimage.setAbstractValueAtPixel(ax, ay, new AbstractValue(output_ab_val.d)); // clone out of fear and respect
                        }
                    }
                }
                result[inputState] = bottom_preimage;
            }
            return(new AbstractImageSpec(result));
        }
Example #2
0
        public AbstractImageSpec WitnessCompose_BottomParam(GrammarRule rule, AbstractImageSpec spec, AbstractImageSpec topSpec)
        {
            Program.DEBUG("Entered WitnessCompose_BottomParam");
            var result = new Dictionary <State, object>();

            foreach (var example in spec.AbstractImageExamples)
            {
                State inputState = example.Key;
                var   output     = example.Value as AbstractImage;
                if (output.ContainsNoneValue())
                {
                    Program.DEBUG("null from WitnessCompose_BottomParam --> output contained NONE value");
                    return(null);
                }
                AbstractImage top_image = (AbstractImage)topSpec.AbstractImageExamples[inputState];
                // If either the top_image or output contain a pixel with "NONE" as output, then
                // it's an invalid candidate image
                if (top_image.ContainsNoneValue())
                {
                    Program.DEBUG("null from WitnessCompose_BottomParam --> top contained NONE value");
                    return(null);
                }


                // TODO: Handle different dimensions for bottom_preimage, currently we assume output is proper dimension
                // Future Idea: use NONE values or some sort of NEGATIVE value to indicate "out of bounds, but still a
                // viable candidate if a top image overwhelmed me. Could make all images arbitrarily sized, like 100x100 or something
                // to enable composition
                AbstractImage bottom_preimage = new AbstractImage(output.x, output.y, output.w, output.h);
                for (int ay = bottom_preimage.y; ay < bottom_preimage.y + bottom_preimage.h; ay++)
                {
                    for (int ax = bottom_preimage.x; ax < bottom_preimage.x + bottom_preimage.w; ax++)
                    {
                        AbstractValue output_ab_val = output.GetAbstractValueAtPixel(ax, ay);
                        if (top_image.InBounds(ax, ay)) // Checking that the x and y coords are in the bounds for top_image
                        {
                            AbstractValue top_image_ab_val = top_image.GetAbstractValueAtPixel(ax, ay);
                            // ONLY could allow 0 on output (thus top and bottom must both be 0)
                            if (output_ab_val.Equals(AbstractConstants.ZERO))
                            {
                                // If the top image isn't ONLY 0, then it's impossible to produce an output that is ONLY 0
                                if (!top_image_ab_val.Equals(AbstractConstants.ZERO))
                                {
                                    Program.DEBUG("null from WitnessCompose_BottomParam --> top image didn't allow 0");
                                    return(null);
                                }
                                // Top image IS only 0, so the only value must be 0 for the bottom preimage
                                else
                                {
                                    bottom_preimage.SetAbstractValueAtPixel(ax, ay,
                                                                            new AbstractValue(AbstractConstants.ZERO));
                                }
                            }
                            // Output is ONLY nonzeros
                            else if (!output_ab_val.AllowsColor(0))
                            {
                                // If the top_image doesn't allow 0, that's cool.
                                // It means that our bottom_preimage can contain literally anything
                                // since its contents will be completely ignored
                                if (!top_image_ab_val.AllowsColor(0))
                                {
                                    // But, the abstract domains must be equivalent between output and top in this case
                                    if (top_image_ab_val.Equals(output_ab_val))
                                    {
                                        bottom_preimage.SetAbstractValueAtPixel(ax, ay,
                                                                                new AbstractValue(AbstractConstants.ANY));
                                    }
                                    // Otherwise, no bottom preimage could be generated to satisfy this
                                    else
                                    {
                                        Program.DEBUG("null from WitnessCompose_BottomParam --> top != output");
                                        return(null);
                                    }
                                }
                                // otherwise, if top image does allow 0, our bottom preimage
                                // takes on the the nonzero values in output
                                // Example:
                                // output: [1,2,3]
                                // top: [0,1,2,3]
                                // bottom: [1,2,3]
                                else
                                {
                                    AbstractValue nonzero_top_image_ab_vals = AbstractValue.Intersect(
                                        new AbstractValue(AbstractConstants.NONZERO),
                                        top_image_ab_val
                                        );
                                    // First, sanity check! Ensure the nonzero elements of top
                                    // are contained within output, otherwise that's bad and we return null
                                    if (!output_ab_val.ContainsAllColors(nonzero_top_image_ab_vals))
                                    {
                                        Program.DEBUG("null from WitnessCompose_BottomParam --> output val wasn't superset of nonzero top vals");
                                        return(null);
                                    }
                                    // Now, easy-peasy, just set bottom_preimage to output
                                    bottom_preimage.SetAbstractValueAtPixel(ax, ay, output_ab_val.Clone());
                                }
                            }
                            // output contains nonzero AND allows 0
                            else if (output_ab_val.AllowsColor(0) && output_ab_val.HammingWeight() > 1)
                            {
                                // If the top_image doesn't allow 0, that's bad!
                                // means we can't get 0 on output, so return null
                                if (!top_image_ab_val.AllowsColor(0))
                                {
                                    Program.DEBUG("null from WitnessCompose_BottomParam --> top image didn't allow 0, which is impossible given output accepts zero (and some other nonzeros)");
                                    return(null);
                                }
                                // otherwise, if top image does allow 0, our bottom preimage is the values on output
                                // Example:
                                // output: [0,1,2,3]
                                // top: [0,1]
                                // bottom: [0,1,2,3]
                                else
                                {
                                    // First, sanity check! Ensure the elements of top
                                    // are contained within elementss of output, invalid
                                    if (!output_ab_val.ContainsAllColors(top_image_ab_val))
                                    {
                                        Program.DEBUG("null from WitnessCompose_BottomParam --> nonzero output val wasn't superset of nonzero top vals");
                                        return(null);
                                    }
                                    // Now, set to the values of output
                                    bottom_preimage.SetAbstractValueAtPixel(ax, ay, output_ab_val.Clone());
                                }
                            }
                            else
                            {
                                throw new Exception("We should not have thrown this. Check WitnessCompose_BottomParam.");
                            }
                        }
                        else
                        {
                            bottom_preimage.SetAbstractValueAtPixel(ax, ay, output_ab_val.Clone()); // clone out of fear and respect
                        }
                    }
                }
                result[inputState] = bottom_preimage;
            }
            return(new AbstractImageSpec(result));
        }